/*
 * Copyright (c) 2022 Huawei Device Co., Ltd.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

 import java.util.ArrayList;
 import java.util.Collections;
 class Gbemu {
     public final static double GBEMU_DURATION = 0.000020833333110203966;
     public final static int GBEMU_0 = 0;
     public final static int GBEMU_1 = 1;
     public final static int GBEMU_2 = 2;
     public final static int GBEMU_3 = 3;
     public final static int GBEMU_4 = 4;
     public final static int GBEMU_5 = 5;
     public final static int GBEMU_6 = 6;
     public final static int GBEMU_7 = 7;
     public final static int GBEMU_8 = 8;
     public final static int GBEMU_9 = 9;
     public final static int GBEMU_10 = 10;
     public final static int GBEMU_11 = 11;
     public final static int GBEMU_12 = 12;
     public final static int GBEMU_13 = 13;
     public final static int GBEMU_14 = 14;
     public final static int GBEMU_15 = 15;
     public final static int GBEMU_16 = 16;
     public final static int GBEMU_17 = 17;
     public final static int GBEMU_18 = 18;
     public final static int GBEMU_19 = 19;
     public final static int GBEMU_20 = 20;
     public final static int GBEMU_21 = 21;
     public final static int GBEMU_22 = 22;
     public final static int GBEMU_23 = 23;
     public final static int GBEMU_24 = 24;
     public final static int GBEMU_25 = 25;
     public final static int GBEMU_26 = 26;
     public final static int GBEMU_27 = 27;
     public final static int GBEMU_28 = 28;
     public final static int GBEMU_29 = 29;
     public final static int GBEMU_30 = 30;
     public final static int GBEMU_31 = 31;
     public final static int GBEMU_32 = 32;
     public final static int GBEMU_33 = 33;
     public final static int GBEMU_34 = 34;
     public final static int GBEMU_35 = 35;
     public final static int GBEMU_36 = 36;
     public final static int GBEMU_37 = 37;
     public final static int GBEMU_38 = 38;
     public final static int GBEMU_39 = 39;
     public final static int GBEMU_40 = 40;
     public final static int GBEMU_88 = 88;
     public final static int GBEMU_90 = 90;
     public final static int GBEMU_41 = 41;
     public final static int GBEMU_42 = 42;
     public final static int GBEMU_43 = 43;
     public final static int GBEMU_44 = 44;
     public final static int GBEMU_45 = 45;
     public final static int GBEMU_46 = 46;
     public final static int GBEMU_47 = 47;
     public final static int GBEMU_48 = 48;
     public final static int GBEMU_49 = 49;
     public final static int GBEMU_50 = 50;
     public final static int GBEMU_51 = 51;
     public final static int GBEMU_52 = 52;
     public final static int GBEMU_53 = 53;
     public final static int GBEMU_54 = 54;
     public final static int GBEMU_55 = 55;
     public final static int GBEMU_56 = 56;
     public final static int GBEMU_57 = 57;
     public final static int GBEMU_58 = 58;
     public final static int GBEMU_59 = 59;
     public final static int GBEMU_60 = 60;
     public final static int GBEMU_61 = 61;
     public final static int GBEMU_62 = 62;
     public final static int GBEMU_63 = 63;
     public final static int GBEMU_72 = 72;
     public final static int GBEMU_80 = 80;
     public final static int GBEMU_64 = 64;
     public final static int GBEMU_96 = 96;
     public final static int GBEMU_127 = 127;
     public final static int GBEMU_128 = 128;
     public final static int GBEMU_144 = 144;
     public final static int GBEMU_160 = 160;
     public final static int GBEMU_225 = 225;
     public final static int GBEMU_252 = 252;
     public final static int GBEMU_256 = 256;
     public final static int GBEMU_512 = 512;
     public final static int GBEMU_1000 = 1000;
     public final static int GBEMU_1024 = 1024;
     public final static int GBEMU_1985 = 1985;
     public final static int GBEMU_4096 = 4096;
     public final static int GBEMU_456 = 456;
     public final static int GBEMU_298 = 298;
     public final static int GBEMU_143 = 143;
     public final static int GBEMU_154 = 154;
     public final static int GBEMU_168 = 168;
     public final static int GBEMU_74 = 74;
     public final static int GBEMU_82 = 82;
     public final static int GBEMU_222 = 222;
     public final static int GBEMU_255 = 255;
     public final static int GBEMU_239 = 239;
     public final static int GBEMU_69120 = 69120;
     public final static int GBEMU_248 = 248;
     public final static int GBEMU_153 = 153;
     public final static int GBEMU_312 = 312;
     public final static int GBEMU_5016 = 5016;
     public final static int GBEMU_100 = 100;
     public final static int GBEMU_2047 = 2047;
     public final static int GBEMU_8192 = 8192;
     public final static int GBEMU_92160 = 92160;
     public final static int GBEMU_250000 = 250000;
     public final static int GBEMU_15000 = 15000;
     public final static int GBEMU_44100 = 44100;
     public final static int GBEMU_25000 = 25000;
     public final static int GBEMU_23040 = 23040;
     public final static int GBEMU_27044 = 27044;
     public final static int GBEMU_48000 = 48000;
     public final static int GBEMU_0xFF50 = 0xff50;
     public final static int GBEMU_0x50 = 0x50;
     public final static int GBEMU_0xFF6C = 0xff6c;
     public final static int GBEMU_0x6C = 0x6c;
     public final static int GBEMU_0x143 = 0x143;
     public final static int GBEMU_0xFF74 = 0xff74;
     public final static int GBEMU_0x74 = 0x74;
     public final static int GBEMU_0xFF70 = 0xff70;
     public final static int GBEMU_0x70 = 0x70;
     public final static int GBEMU_0x10 = 0x10;
     public final static int GBEMU_0xFF6B = 0xff6b;
     public final static int GBEMU_0x6B = 0x6b;
     public final static int GBEMU_0xFF6A = 0xff6a;
     public final static int GBEMU_0x6A = 0x6a;
     public final static int GBEMU_0xFF69 = 0xff69;
     public final static int GBEMU_0x69 = 0x69;
     public final static int GBEMU_0xFF68 = 0xff68;
     public final static int GBEMU_0x68 = 0x68;
     public final static int GBEMU_0xFF55 = 0xff55;
     public final static int GBEMU_0x55 = 0x55;
     public final static int GBEMU_0xFF4F = 0xff4f;
     public final static int GBEMU_0x4F = 0x4f;
     public final static int GBEMU_0x4D = 0x4d;
     public final static int GBEMU_0xFF4D = 0xff4d;
     public final static int GBEMU_0x49 = 0x49;
     public final static int GBEMU_0xFF49 = 0xff49;
     public final static int GBEMU_0x48 = 0x48;
     public final static int GBEMU_0x1 = 0x1;
     public final static int GBEMU_0xFF48 = 0xff48;
     public final static int GBEMU_0xFF47 = 0xff47;
     public final static int GBEMU_0x47 = 0x47;
     public final static int GBEMU_0xFEA0 = 0xfea0;
     public final static int GBEMU_0xFF46 = 0xff46;
     public final static int GBEMU_0x46 = 0x46;
     public final static int GBEMU_0xFE00 = 0xfe00;
     public final static int GBEMU_0x41 = 0x41;
     public final static int GBEMU_0xFF41 = 0xff41;
     public final static int GBEMU_0x2 = 0x2;
     public final static int GBEMU_0x08 = 0x08;
     public final static int GBEMU_0x20 = 0x20;
     public final static int GBEMU_0x40 = 0x40;
     public final static int GBEMU_0xE0 = 0xe0;
     public final static int GBEMU_0x7F = 0x7f;
     public final static int GBEMU_0x78 = 0x78;
     public final static int GBEMU_0xFF40 = 0xff40;
     public final static int GBEMU_0x01 = 0x01;
     public final static int GBEMU_0x02 = 0x02;
     public final static int GBEMU_0x04 = 0x04;
     public final static int GBEMU_0x400 = 0x400;
     public final static int GBEMU_0x80 = 0x80;
     public final static int GBEMU_0xFF44 = 0xff44;
     public final static int GBEMU_0xFF02 = 0xff02;
     public final static int GBEMU_0xD000 = 0xd000;
     public final static int GBEMU_0xE000 = 0xe000;
     public final static int GBEMU_0x2000 = 0x2000;
     public final static int GBEMU_0x07 = 0x07;
     public final static int GBEMU_0xFF51 = 0xff51;
     public final static int GBEMU_0xFF52 = 0xff52;
     public final static int GBEMU_0x3F = 0x3f;
     public final static int GBEMU_0xFF = 0xff;
     public final static int GBEMU_0xFF54 = 0xff54;
     public final static int GBEMU_0x54 = 0x54;
     public final static int GBEMU_0xF0 = 0xf0;
     public final static int GBEMU_0x53 = 0x53;
     public final static int GBEMU_0xFF53 = 0xff53;
     public final static int GBEMU_0x52 = 0x52;
     public final static int GBEMU_0x51 = 0x51;
     public final static int GBEMU_0x7f = 0x7f;
     public final static int GBEMU_0xff = 0xff;
     public final static int GBEMU_0xFFFFFF = 0xffffff;
     public final static int GBEMU_0x00 = 0x00;
     public final static int GBEMU_0x13 = 0x13;
     public final static int GBEMU_0xD8 = 0xd8;
     public final static int GBEMU_0x014D = 0x014d;
     public final static int GBEMU_0xFFFE = 0xfffe;
     public final static int GBEMU_0x0100 = 0x0100;
     public final static int GBEMU_0xA000 = 0xa000;
     public final static int GBEMU_0xF000 = 0xf000;
     public final static int GBEMU_0xEFFFDE = 0xefffde;
     public final static int GBEMU_0xADD794 = 0xadd794;
     public final static int GBEMU_0x529273 = 0x529273;
     public final static int GBEMU_0x183442 = 0x183442;
     public final static int GBEMU_0x0F = 0x0f;
     public final static int GBEMU_0x7C = 0x7c;
     public final static int GBEMU_0xF8 = 0xf8;
     public final static int GBEMU_0xBF = 0xbf;
     public final static int GBEMU_0xF3 = 0xf3;
     public final static int GBEMU_0x77 = 0x77;
     public final static int GBEMU_0xF1 = 0xf1;
     public final static int GBEMU_0xFC = 0xfc;
     public final static int GBEMU_0x3E = 0x3e;
     public final static int GBEMU_0x9F = 0x9f;
     public final static int GBEMU_0x7E = 0x7e;
     public final static int GBEMU_0xFE = 0xfe;
     public final static int GBEMU_0x91 = 0x91;
     public final static int GBEMU_0x8F = 0x8f;
     public final static int GBEMU_0xC0 = 0xc0;
     public final static int GBEMU_0x0B = 0x0b;
     public final static int GBEMU_0xDC = 0xdc;
     public final static int GBEMU_0xDD = 0xdd;
     public final static int GBEMU_0x03 = 0x03;
     public final static int GBEMU_0xCE = 0xce;
     public final static int GBEMU_0xED = 0xed;
     public final static int GBEMU_0xC1 = 0xc1;
     public final static int GBEMU_0xE6 = 0xe6;
     public final static int GBEMU_0x83 = 0x83;
     public final static int GBEMU_0x6E = 0x6e;
     public final static int GBEMU_0x99 = 0x99;
     public final static int GBEMU_0x3D = 0x3d;
     public final static int GBEMU_0x36 = 0x36;
     public final static int GBEMU_0xD3 = 0xd3;
     public final static int GBEMU_0x45 = 0x45;
     public final static int GBEMU_0xBB = 0xbb;
     public final static int GBEMU_0xD0 = 0xd0;
     public final static int GBEMU_0x98 = 0x98;
     public final static int GBEMU_0x7A = 0x7a;
     public final static int GBEMU_0xEC = 0xec;
     public final static int GBEMU_0xEF = 0xef;
     public final static int GBEMU_0xD1 = 0xd1;
     public final static int GBEMU_0x67 = 0x67;
     public final static int GBEMU_0x66 = 0x66;
     public final static int GBEMU_0x1F = 0x1f;
     public final static int GBEMU_0xCC = 0xcc;
     public final static int GBEMU_0x0D = 0x0d;
     public final static int GBEMU_0x63 = 0x63;
     public final static int GBEMU_0x89 = 0x89;
     public final static int GBEMU_0xB7 = 0xb7;
     public final static int GBEMU_0xC2 = 0x11;
     public final static int GBEMU_0x11 = 0x11;
     public final static int GBEMU_0x71 = 0x71;
     public final static int GBEMU_0xFA = 0xfa;
     public final static int GBEMU_0x88 = 0x88;
     public final static int GBEMU_0xF4 = 0xf4;
     public final static int GBEMU_0x9E = 0x9e;
     public final static int GBEMU_0xF9 = 0xf9;
     public final static int GBEMU_0x0E = 0x0e;
     public final static int GBEMU_0x86 = 0x86;
     public final static int GBEMU_0x5F = 0x5f;
     public final static int GBEMU_0x24 = 0x24;
     public final static int GBEMU_0x5D = 0x5d;
     public final static int GBEMU_0x73 = 0x73;
     public final static int GBEMU_0xFD = 0xfd;
     public final static int GBEMU_0x6D = 0x6d;
     public final static int GBEMU_0x12 = 0x12;
     public final static int GBEMU_0x1D = 0x1d;
     public final static int GBEMU_0x2F = 0x2f;
     public final static int GBEMU_0x75 = 0x75;
     public final static int GBEMU_0x05 = 0x05;
     public final static int GBEMU_0x81 = 0x81;
     public final static int GBEMU_0xB4 = 0xb4;
     public final static int GBEMU_0x0C = 0x0c;
     public final static int GBEMU_0xB9 = 0xb9;
     public final static int GBEMU_0xD9 = 0xd9;
     public final static int GBEMU_0x33 = 0x33;
     public final static int GBEMU_0x97 = 0x97;
     public final static int GBEMU_0xE5 = 0xe5;
     public final static int GBEMU_0x5E = 0x5e;
     public final static int GBEMU_0x06 = 0x06;
     public final static int GBEMU_0xD5 = 0xd5;
     public final static int GBEMU_0xAA = 0xaa;
     public final static int GBEMU_0x3A = 0x3a;
     public final static int GBEMU_0x418 = 0x418;
     public final static int GBEMU_0x7FFF = 0x7fff;
     public final static int GBEMU_0x200 = 0x200;
     public final static int GBEMU_0x800 = 0x800;
     public final static int GBEMU_0x100 = 0x100;
     public final static int GBEMU_0xFFFF = 0xffff;
     public final static int GBEMU_0xF = 0xf;
     public final static int GBEMU_0xFFF = 0xfff;
     public final static int GBEMU_0x60 = 0x60;
     public final static int GBEMU_0x26 = 0x26;
     public final static int GBEMU_0xFF26 = 0xff26;
     public final static int GBEMU_0xFF27 = 0xff27;
     public final static int GBEMU_0xFF28 = 0xff28;
     public final static int GBEMU_0xFF29 = 0xff29;
     public final static int GBEMU_0xFF2A = 0xff2a;
     public final static int GBEMU_0xFF2B = 0xff2b;
     public final static int GBEMU_0xFF2C = 0xff2c;
     public final static int GBEMU_0xFF2D = 0xff2d;
     public final static int GBEMU_0xFF2E = 0xff2e;
     public final static int GBEMU_0xFF2F = 0xff2f;
     public final static int GBEMU_0xFF30 = 0xff30;
     public final static int GBEMU_0xFF31 = 0xff31;
     public final static int GBEMU_0xFF32 = 0xff32;
     public final static int GBEMU_0xFF33 = 0xff33;
     public final static int GBEMU_0xFF34 = 0xff34;
     public final static int GBEMU_0xFF35 = 0xff35;
     public final static int GBEMU_0xFF36 = 0xff36;
     public final static int GBEMU_0xFF37 = 0xff37;
     public final static int GBEMU_0xFF38 = 0xff38;
     public final static int GBEMU_0xFF39 = 0xff39;
     public final static int GBEMU_0xFF3A = 0xff3a;
     public final static int GBEMU_0xFF3B = 0xff3b;
     public final static int GBEMU_0xFF3C = 0xff3c;
     public final static int GBEMU_0xFF3D = 0xff3d;
     public final static int GBEMU_0xFF3E = 0xff3e;
     public final static int GBEMU_0xFF3F = 0xff3f;
     public final static int GBEMU_0xFF00 = 0xff00;
     public final static int GBEMU_0xFF42 = 0xff42;
     public final static int GBEMU_0x42 = 0x42;
     public final static int GBEMU_0xFF43 = 0xff43;
     public final static int GBEMU_0x43 = 0x43;
     public final static int GBEMU_0x44 = 0x44;
     public final static int GBEMU_0xFF4A = 0xff4a;
     public final static int GBEMU_0x4A = 0x4a;
     public final static int GBEMU_0xFF56 = 0xff56;
     public final static int GBEMU_0x3C = 0x3c;
     public final static int GBEMU_0x56 = 0x56;
     public final static int GBEMU_0x6c = 0x6c;
     public final static int GBEMU_0xFF75 = 0xff75;
     public final static int GBEMU_0xFF76 = 0xff76;
     public final static int GBEMU_0xFF77 = 0xff77;
     public final static int GBEMU_0xA060 = 0xa060;
     public final static int GBEMU_0xA070 = 0xa070;
     public final static int GBEMU_0xA080 = 0xa080;
     public final static int GBEMU_0xA050 = 0xa050;
     public final static int GBEMU_0xA040 = 0xa040;
     public final static int GBEMU_0xA030 = 0xa030;
     public final static int GBEMU_0xA020 = 0xa020;
     public final static int GBEMU_0x09 = 0x09;
     public final static int GBEMU_0x0A = 0x0a;
     public final static int GBEMU_0x0000 = 0x0000;
     public final static int GBEMU_0x8000 = 0x8000;
     public final static int GBEMU_0x4000 = 0x4000;
     public final static int GBEMU_0x6000 = 0x6000;
     public final static int GBEMU_0x1000 = 0x1000;
     public final static int GBEMU_0x2100 = 0x2100;
     public final static int GBEMU_0x2200 = 0x2200;
     public final static int GBEMU_0x3000 = 0x3000;
     public final static int GBEMU_0x9000 = 0x9000;
     public final static int GBEMU_0x9800 = 0x9800;
     public final static int GBEMU_0xC000 = 0xc000;
     public final static int GBEMU_0x1FFF = 0x1fff;
     public final static int GBEMU_0xA200 = 0xa200;
     public final static int GBEMU_0x7FF = 0x7ff;
     public final static int GBEMU_0x1800 = 0x1800;
     public final static int GBEMU_0x8001 = 0x8001;
     public final static int GBEMU_0x8002 = 0x8002;
     public final static int GBEMU_0x8003 = 0x8003;
     public final static int GBEMU_0x8004 = 0x8004;
     public final static int GBEMU_0x8005 = 0x8005;
     public final static int GBEMU_0x8006 = 0x8006;
     public final static int GBEMU_0x8007 = 0x8007;
     public final static int GBEMU_0x8008 = 0x8008;
     public final static int GBEMU_0x8009 = 0x8009;
     public final static int GBEMU_0x800A = 0x800a;
     public final static int GBEMU_0x800B = 0x800b;
     public final static int GBEMU_0x800C = 0x800c;
     public final static int GBEMU_0x800D = 0x800d;
     public final static int GBEMU_0x800E = 0x800e;
     public final static int GBEMU_0x800F = 0x800f;
     public final static int GBEMU_0x7F0 = 0x7f0;
     public final static int GBEMU_0x1FF0 = 0x1ff0;
     public final static int GBEMU_0xFFF0 = 0xfff0;
     public final static int GBEMU_0x3 = 0x3;
     public final static int GBEMU_0x4 = 0x4;
     public final static int GBEMU_0x5 = 0x5;
     public final static int GBEMU_0x6 = 0x6;
     public final static int GBEMU_0x7 = 0x7;
     public final static int GBEMU_0x8 = 0x8;
     public final static int GBEMU_0x9 = 0x9;
     public final static int GBEMU_0xA = 0xa;
     public final static int GBEMU_0xB = 0xb;
     public final static int GBEMU_0xC = 0xc;
     public final static int GBEMU_0xD = 0xd;
     public final static int GBEMU_0xE = 0xe;
     public final static int GBEMU_0x30 = 0x30;
     public final static int GBEMU_0xFF01 = 0xff01;
     public final static int GBEMU_0xFF04 = 0xff04;
     public final static int GBEMU_0xFF05 = 0xff05;
     public final static int GBEMU_0xFF06 = 0xff06;
     public final static int GBEMU_0xFF07 = 0xff07;
     public final static int GBEMU_0xFF0F = 0xff0f;
     public final static int GBEMU_0xFF10 = 0xff10;
     public final static int GBEMU_0xFF11 = 0xff11;
     public final static int GBEMU_0xFF12 = 0xff12;
     public final static int GBEMU_0xFF13 = 0xff13;
     public final static int GBEMU_0xFF14 = 0xff14;
     public final static int GBEMU_0x700 = 0x700;
     public final static int GBEMU_0x0 = 0x0;
     public final static int GBEMU_0x14 = 0x14;
     public final static int GBEMU_0xFF16 = 0xff16;
     public final static int GBEMU_0x16 = 0x16;
     public final static int GBEMU_0xFF17 = 0xff17;
     public final static int GBEMU_0x17 = 0x17;
     public final static int GBEMU_0xFF18 = 0xff18;
     public final static int GBEMU_0x18 = 0x18;
     public final static int GBEMU_0xFF19 = 0xff19;
     public final static int GBEMU_0x19 = 0x19;
     public final static int GBEMU_0xFF1A = 0xff1a;
     public final static int GBEMU_0x1A = 0x1a;
     public final static int GBEMU_0xFF1B = 0xff1b;
     public final static int GBEMU_0x1B = 0x1b;
     public final static int GBEMU_0xFF1C = 0xff1c;
     public final static int GBEMU_0x1C = 0x1c;
     public final static int GBEMU_0xFF1D = 0xff1d;
     public final static int GBEMU_0xFF1E = 0xff1e;
     public final static int GBEMU_0x1E = 0x1e;
     public final static int GBEMU_0x21 = 0x21;
     public final static int GBEMU_0x22 = 0x22;
     public final static int GBEMU_0x23 = 0x23;
     public final static int GBEMU_0x25 = 0x25;
     public final static int GBEMU_0x27 = 0x27;
     public final static int GBEMU_0x28 = 0x28;
     public final static int GBEMU_0x29 = 0x29;
     public final static int GBEMU_0xFF20 = 0xff20;
     public final static int GBEMU_0xFF21 = 0xff21;
     public final static int GBEMU_0xFF22 = 0xff22;
     public final static int GBEMU_0xFF23 = 0xff23;
     public final static int GBEMU_0xFF24 = 0xff24;
     public final static int GBEMU_0xFF25 = 0xff25;
     public final static int GBEMU_0x2A = 0x2a;
     public final static int GBEMU_0x2B = 0x2b;
     public final static int GBEMU_0x2C = 0x2c;
     public final static int GBEMU_0x2E = 0x2e;
     public final static int GBEMU_0x2D = 0x2d;
     public final static int GBEMU_0x31 = 0x31;
     public final static int GBEMU_0x32 = 0x32;
     public final static int GBEMU_0x34 = 0x34;
     public final static int GBEMU_0x35 = 0x35;
     public final static int GBEMU_0x37 = 0x37;
     public final static int GBEMU_0x38 = 0x38;
     public final static int GBEMU_0x39 = 0x39;
     public final static int GBEMU_0x3B = 0x3b;
     public final static int GBEMU_0xFF45 = 0xff45;
     public final static int GBEMU_0xFF4B = 0xff4b;
     public final static int GBEMU_0x4B = 0x4b;
     public final static int GBEMU_0xFF72 = 0xff72;
     public final static int GBEMU_0xFF73 = 0xff73;
     public final static int GBEMU_0x72 = 0x72;
     public final static int GBEMU_0x76 = 0x76;
     public final static int GBEMU_0x0080 = 0x0080;
     public final static int GBEMU_0x0001 = 0x0001;
     public final static int GBEMU_0xFF80 = 0xff80;
     public final static int GBEMU_0xF00 = 0xf00;
     public final static int GBEMU_0x0200 = 0x0200;
     public final static int GBEMU_0x0002 = 0x0002;
     public final static int GBEMU_0x0400 = 0x0400;
     public final static int GBEMU_0x0004 = 0x0004;
     public final static int GBEMU_0x0800 = 0x0800;
     public final static int GBEMU_0x0008 = 0x0008;
     public final static int GBEMU_0x0010 = 0x0010;
     public final static int GBEMU_0x0020 = 0x0020;
     public final static int GBEMU_0x0040 = 0x0040;
     public final static int GBEMU_0xFEFF = 0xfeff;
     public final static int GBEMU_0xFDFF = 0xfdff;
     public final static int GBEMU_0xFFFD = 0xfffd;
     public final static int GBEMU_0xFF1F = 0xff1f;
     public final static int GBEMU_0x600 = 0x600;
     public final static int GBEMU_0x1FFE = 0x1ffe;
     public final static int GBEMU_0x9FFE = 0x9ffe;
     public final static int GBEMU_0xA00 = 0xa00;
     public final static int GBEMU_0xC00 = 0xc00;
     public final static int GBEMU_0xE00 = 0xe00;
     public final static int GBEMU_0x1000000 = 0x1000000;
     public final static int GBEMU_0x2000000 = 0x2000000;
     public final static int GBEMU_0x1f = 0x1f;
     public final static int GBEMU_0xf80 = 0xf80;
     public final static int GBEMU_0xF8F8F8 = 0xf8f8f8;
     public final static int GBEMU_0x7B = 0x7b;
     public final static int GBEMU_0xf = 0xf;
     public final static int GBEMU_0xF7 = 0xf7;
     public final static int GBEMU_0xFB = 0xfb;
     public final static int GBEMU_0xF0F0 = 0xf0f0;
     public final static int GBEMU_0x1FF = 0x1ff;
     public final static int GBEMU_0x10000 = 0x10000;
     public final static int GBEMU_0x780 = 0x780;
     public final static int GBEMU_0x680 = 0x680;
     public final static int GBEMU_0x500 = 0x500;
     public final static int GBEMU_0x580 = 0x580;
     public final static int GBEMU_0x480 = 0x480;
     public final static int GBEMU_0x380 = 0x380;
     public final static int GBEMU_0x300 = 0x300;
     public final static int GBEMU_0x280 = 0x280;
     public final static int GBEMU_0x180 = 0x180;
     public final static int GBEMU_0x080 = 0x080;
     public final static int GBEMU_0x78000 = 0x78000;
     public final static int GBEMU_0x70000 = 0x70000;
     public final static int GBEMU_0x68000 = 0x68000;
     public final static int GBEMU_0x60000 = 0x60000;
     public final static int GBEMU_0x58000 = 0x58000;
     public final static int GBEMU_0x50000 = 0x50000;
     public final static int GBEMU_0x48000 = 0x48000;
     public final static int GBEMU_0x40000 = 0x40000;
     public final static int GBEMU_0x38000 = 0x38000;
     public final static int GBEMU_0x30000 = 0x30000;
     public final static int GBEMU_0x28000 = 0x28000;
     public final static int GBEMU_0x20000 = 0x20000;
     public final static int GBEMU_0x18000 = 0x18000;
     public final static int GBEMU_0x08000 = 0x08000;
     public final static int GBEMU_0x3FFF = 0x3fff;
     public final static int GBEMU_0x80000 = 0x80000;
     public final static int GBEMU_0x400000 = 0x400000;
     public final static int GBEMU_0x7000 = 0x7000;
     public final static int GBEMU_0x7D = 0x7d;
     public final static int GBEMU_0x900 = 0x900;
     public final static int GBEMU_0x144 = 0x144;
     public final static int GBEMU_0x145 = 0x145;
     public final static int GBEMU_0x14B = 0x14b;
     public final static int GBEMU_0x148 = 0x148;
     public final static int GBEMU_0x149 = 0x149;
     public final static int GBEMU_0x7ff = 0x7ff;
     public final static int GBEMU_0xfe = 0xfe;
     public final static int GBEMU_0x1fff = 0x1fff;
     public final static int GBEMU_0xC3 = 0xc3;
     public final static int GBEMU_0xFFFFFFFF = 0xffffffff;
     public final static int GBEMU_0xFFFFFFFE = 0xfffffffe;
     public final static int GBEMU_0x9A = 0x9a;
     public final static int GBEMU_0xA0 = 0xa0;
     public final static int GBEMU_0x80FF = 0x80ff;
     public final static int GBEMU_0xFBFF = 0xfbff;
     public final static int GBEMU_0xFFFB = 0xfffb;
     public final static int GBEMU_0xF7FF = 0xf7ff;
     public final static int GBEMU_0xFFF7 = 0xfff7;
     public final static int GBEMU_0xEFFF = 0xefff;
     public final static int GBEMU_0xFFEF = 0xffef;
     public final static int GBEMU_0xDF = 0xdf;
     public final static int GBEMU_0xDFFF = 0xdfff;
     public final static int GBEMU_0xFFDF = 0xffdf;
     public final static int GBEMU_0xBFFF = 0xbfff;
     public final static int GBEMU_0xFFBF = 0xffbf;
     public final static int GBEMU_0xFF7F = 0xff7f;
     public final static int GBEMU_0x101 = 0x101;
     public final static int GBEMU_0x134 = 0x134;
     public final static int GBEMU_0x13F = 0x13f;
     public final static int GBEMU_0x147 = 0x147;
 
     public static String expectedGameboyStateStr = "{'registerA':160,'registerB':255,'registerC':255,'registerE':11,'registersHL':51600,'programCounter':24309,'stackPointer':49706,'sumrom':10171578,'sumMemory':3435856,'summbcRam':234598,'sumVRam':0}";
 
 // Start of browser emulation.
 
     public static class GameBoyWindowClass {
         boolean opera = false;
         boolean mozRequestAnimationFrame = false;
     }
 
     public static GameBoyWindowClass gameBoyWindow = new GameBoyWindowClass();
 
     public static class GameBoyContext {
         public GameBoyContextImageDataResult createImageData(int w, int h) {
             GameBoyContextImageDataResult result = new GameBoyContextImageDataResult();
             result.data = new ArrayList<>(Collections.nCopies(w * h * GBEMU_4, 0));
             return result;
         }
        public  void putImageData(GameBoyContextImageDataResult buffer, int x, int y) {
             int sum = 0;
             for (int i = 0; i < buffer.data.size(); i++) {
                 sum += i * buffer.data.get(i);
                 sum = sum % GBEMU_1000;
             }
         }
         public void drawImage(GameBoyCanvas canvas, int x, int y, int screenWidth, int screenHeight) {
         }
     }
     public static class GameBoyContextImageDataResult {
         public ArrayList<Integer> data = new ArrayList<>();
     }
 
     public static class GameBoyCanvas {
         public int width = GBEMU_160;
         public int height = GBEMU_144;
         public int clientWidth = 0;
         public int clientHeight = 0;
         public GameBoyCanvasStyle style = new GameBoyCanvasStyle();
         public GameBoyContext getContext(String type) {
             return new GameBoyContext();
         }
     }
 
     public static class GameBoyCanvasStyle {
         String visibility = "visibile";
     }
 
     public static void cout(String message, int colorIndex) {}
 
     public static class GameBoyAudioNodeConstrc {
         public int bufferSize = 0;
         public GameBoyAudioNodeBuffer outputBuffer = null;
         public GbemuPartOnaudioprocess onaudioprocess = null;
         public void connect(GameBoyAudioContextDestination destination) {}
         public void run() {
             GameBoyAudioNodeEvent event = new GameBoyAudioNodeEvent();
             event.outputBuffer = this.outputBuffer;
             this.onaudioprocess.call(event);
         }
     }
 
     public static GameBoyAudioNodeConstrc gameBoyAudioNode = new GameBoyAudioNodeConstrc();
 
     public static class GameBoyAudioNodeEvent {
         public GameBoyAudioNodeBuffer outputBuffer = null;
     }
 
     public static class GameBoyAudioNodeBuffer {
         public ArrayList<Integer[]> channelData = new ArrayList<>();
         public Integer[] getChannelData(int i) {
             return this.channelData.get(i);
         }
     }
 
     public static class GameBoyAudioContext {
         public int sampleRate = GBEMU_48000;
         public GameBoyAudioContextDestination destination = new GameBoyAudioContextDestination();
         public GameBoyAudioContextBufferSource createBufferSource() {
             return new GameBoyAudioContextBufferSource();
         }
         public GameBoyAudioContextBuffer createBuffer(int channels, int len, int sampleRate) {
             return new GameBoyAudioContextBuffer(1, 1, 1, GBEMU_DURATION, GBEMU_48000);
         }
         public GameBoyAudioNodeConstrc createJavaScriptNode(int bufferSize, int inputChannels, int outputChannels) {
             gameBoyAudioNode.bufferSize = bufferSize;
             gameBoyAudioNode.outputBuffer = new GameBoyAudioNodeBuffer();
             for (int i = 0; i < outputChannels; i++) {
                 gameBoyAudioNode.outputBuffer.channelData.add(new Integer[bufferSize]);
             }
             return gameBoyAudioNode;
         }
     }
 
     public static class GameBoyAudioContextBufferSource {
         public boolean loop = false;
         public GameBoyAudioContextBuffer buffer = null;
         public void noteOn(int index) {}
         public void connect(GameBoyAudioNodeConstrc audioNode) {}
     }
 
     public static class GameBoyAudioContextDestination {}
 
     public static class GameBoyAudioContextBuffer {
         public int gain;
         public int numberOfChannels;
         public int length;
         public double duration;
         public int sampleRate;
         GameBoyAudioContextBuffer(int gain, int numberOfChannels, int length, double duration, int sampleRate) {
             this.gain = gain;
             this.numberOfChannels = numberOfChannels;
             this.length = length;
             this.duration = duration;
             this.sampleRate = sampleRate;
         }
     }
 
     public static int mockDateTimeCounter = 0;
 
     public static class NewDate {
         public int getTime() {
             mockDateTimeCounter += GBEMU_16;
             return mockDateTimeCounter;
         }
     }
 
 // End of browser emulation.
 
 // Start of helper functions.
 
     public static void checkFinalState() {
         String stateStr = String.format("{'registerA':%d,'registerB':%d,'registerC':%d,'registerE':%d,'registersHL':%d,'programCounter':%d,'stackPointer':%d,'sumrom':%d,'sumMemory':%d,'summbcRam':%d,'sumVRam':%d}", gameboy.registerA, gameboy.registerB, gameboy.registerC, gameboy.registerE, gameboy.registersHL, gameboy.programCounter, gameboy.stackPointer, setStateSum(gameboy.fromTypedArray(gameboy.rom)), setStateSum(gameboy.fromTypedArray(gameboy.memory)), setStateSum(gameboy.fromTypedArray(gameboy.mbcRam)), setStateSum(gameboy.fromTypedArray(gameboy.vram)));
         if (expectedGameboyStateStr.length() > 0) {
             if (stateStr != expectedGameboyStateStr) {
             }
         } else {
         }
     }
 
     public static int setStateSum(ArrayList<Integer> a) {
         int result = 0;
         for (int i = 0; i < a.size(); i++) {
             result += a.get(i);
         }
         return result;
     }
 
     public static void resetGlobalVariables() {
         debugLog("This is resetGlobalVariables");
         //Audio API Event Handler:
         audioContextHandle = null;
         audioNode = null;
         audioSource = null;
         launchedContext = false;
         audioContextSampleBuffer = new ArrayList();
         resampled = new ArrayList();
         webAudioMinBufferSize = GBEMU_15000;
         webAudioMaxBufferSize = GBEMU_25000;
         webAudioActualSampleRate = GBEMU_44100;
         xAudioJSSampleRate = 0;
         webAudioMono = false;
         xAudioJSVolume = 1;
         resampleControl = null;
         audioBufferSize = 0;
         resampleBufferStart = 0;
         resampleBufferEnd = 0;
         resampleBufferSize = GBEMU_2;
         gameboy = null; //GameBoyCore object.
     }
 
     // End of helper functions.
 
 // Original code from Grant Galitz follows.
 // Modifications by Google are marked in comments.
 
 // Start of js/other/base64.js file.
 
     public String toBase64Table = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
 // End of js/other/base64.js file.
 
 // Start of js/other/resampler.js file.
 
     //JavaScript Audio Resampler (c) 2011 - Grant Galitz
     public static class Resampler {
         public int fromSampleRate = 0;
         public int toSampleRate = 0;
         public int channels = 0;
         public static int outputBufferSize = 0;
         public static boolean noReturn = false;
         public GbemuPartResampler resampler = null;
         public static int ratioWeight = 0;
         public static boolean tailExists = false;
         public static double lastWeight = 0;
         public static ArrayList<Integer> lastOutput = new ArrayList<>();
         public static ArrayList<Integer> outputBuffer = new ArrayList<>();
         Resampler(int fromSampleRate, int toSampleRate, int channels, int outputBufferSize, boolean noReturn) {
             this.fromSampleRate = fromSampleRate;
             this.toSampleRate = toSampleRate;
             this.channels = channels | 0;
             this.outputBufferSize = outputBufferSize;
             this.noReturn = noReturn;
             this.initialize();
         }
         public void initialize() {
             //Perform some checks:
             if (this.fromSampleRate > 0 && this.toSampleRate > 0 && this.channels > 0) {
                 if (this.fromSampleRate == this.toSampleRate) {
                     //Setup a resampler bypass:
                     this.resampler = Resampler::bypassResampler; //Resampler just returns what was passed through.
                     this.ratioWeight = 1;
                 } else {
                     //Setup the interpolation resampler:
                     this.resampler = Resampler::interpolate; //Resampler is a custom quality interpolation algorithm.
                     this.ratioWeight = this.fromSampleRate / this.toSampleRate;
                     this.tailExists = false;
                     this.lastWeight = 0;
                     this.initializeBuffers();
                 }
             } else {
             }
         }
         public static Object interpolate(ArrayList<Integer> buffer) {
             int bufferLength = Math.min(buffer.size(), outputBufferSize);
             if (bufferLength % GBEMU_2 == 0) {
                 if (bufferLength > 0) {
                     int ratioWeights = ratioWeight;
                     double weight = 0;
                     int output0 = 0;
                     int output1 = 0;
                     int actualPosition = 0;
                     double amountToNext = 0;
                     boolean alreadyProcessedTail = !tailExists;
                     tailExists = false;
                     ArrayList<Integer> outputBuffers = outputBuffer;
                     int outputOffset = 0;
                     double currentPosition = 0;
                     do {
                         if (alreadyProcessedTail) {
                             weight = ratioWeights;
                             output0 = 0;
                             output1 = 0;
                         } else {
                             weight = lastWeight;
                             output0 = lastOutput.get(0);
                             output1 = lastOutput.get(1);
                             alreadyProcessedTail = true;
                         }
                         while (weight > 0 && actualPosition < bufferLength) {
                             amountToNext = 1 + actualPosition - currentPosition;
                             if (weight >= amountToNext) {
                                 output0 += buffer.get(actualPosition++) * amountToNext;
                                 output1 += buffer.get(actualPosition++) * amountToNext;
                                 currentPosition = actualPosition;
                                 weight -= amountToNext;
                             } else {
                                 output0 += buffer.get(actualPosition) * weight;
                                 output1 += buffer.get(actualPosition + 1) * weight;
                                 currentPosition += weight;
                                 weight = 0;
                                 break;
                             }
                         }
                         if (weight == 0) {
                             outputBuffers.set(outputOffset++, (output0 / ratioWeights));
                             outputBuffers.set(outputOffset++, (output1 / ratioWeights));
                         } else {
                             lastWeight = weight;
                             lastOutput.set(0, output0);
                             lastOutput.set(1, output1);
                             tailExists = true;
                             break;
                         }
                     } while (actualPosition < bufferLength);
                     return bufferSlice(outputOffset);
                 } else {
                     return noReturn ? 0 : new ArrayList<Integer>();
                 }
             } else {
             }
             return new ArrayList<Integer>();
         };
 
         public static Object bypassResampler(ArrayList<Integer> buffer) {
             if (noReturn) {
                 //Set the buffer passed as our own, as we don't need to resample it:
                 outputBuffer = buffer;
                 return buffer.size();
             } else {
                 //Just return the buffer passsed:
                 return buffer;
             }
         };
         public static Object bufferSlice(int sliceAmount) {
             if (noReturn) {
                 //If we're going to access the properties directly from this object:
                 return sliceAmount;
             } else {
                 //Typed array and normal array buffer section referencing:
                 return outputBuffer.subList(0, sliceAmount);
             }
         }
         public void initializeBuffers() {
             //Initialize the internal buffer:
             this.outputBuffer = new ArrayList(Collections.nCopies(this.outputBufferSize, 0));
             this.lastOutput = new ArrayList(Collections.nCopies(this.channels, 0));
         }
     }
 
 // End of js/other/resampler.js file.
 
 // Start of js/other/XAudioServer.js file.
 
     /*Initialize here first:
       Example:
         Stereo audio with a sample rate of 70 khz, a minimum buffer of 15000 samples total, a maximum buffer of 25000 samples total and a starting volume level of 1.
           var parentObj = this;
           this.audioHandle = new XAudioServer(GBEMU_2, GBEMU_70000, GBEMU_15000, GBEMU_25000, function (sampleCount) {
             return parentObj.audioUnderRun(sampleCount);
           }, 1);
 
       The callback is passed the number of samples requested, while it can return any number of samples it wants back.
     */
     public static class XAudioServer {
         public int audioChannels = 0;
         public int channels = 0;
         public int sampleRate = 0;
         public int minBufferSize = 0;
         public int maxBufferSize = 0;
         public int volume = 0;
         public int audioType = -1;
         public int[] mozAudioTail = new int[0];
         public Audio audioHandleMoz = null;
         public XAudioServer audioHandleFlash = null;
         public boolean flashInitialized = false;
         public boolean mozAudioFound = false;
         public GbemuPartUnderRunCallback underRunCallback = null;
         XAudioServer(
                 int channels,
                 int sampleRate,
                 int minBufferSize,
                 int maxBufferSize,
                 GbemuPartUnderRunCallback underRunCallback,
                 int volume
         ) {
             this.channels = channels;
             this.sampleRate = sampleRate;
             this.minBufferSize = minBufferSize;
             this.maxBufferSize = maxBufferSize;
             this.volume = volume;
             this.audioChannels = channels == GBEMU_2 ? GBEMU_2 : 1;
             webAudioMono = this.audioChannels == 1;
             xAudioJSSampleRate = sampleRate > 0 && sampleRate <= GBEMU_0xFFFFFF ? sampleRate : GBEMU_44100;
             webAudioMinBufferSize =
                     minBufferSize >= samplesPerCallback << 1 && minBufferSize < maxBufferSize ?
                             minBufferSize & (webAudioMono ? GBEMU_0xFFFFFFFF : GBEMU_0xFFFFFFFE) :
                             samplesPerCallback << 1;
             webAudioMaxBufferSize =
                     Math.floor(maxBufferSize) > webAudioMinBufferSize + this.audioChannels ?
                             maxBufferSize & (webAudioMono ? GBEMU_0xFFFFFFFF : GBEMU_0xFFFFFFFE) :
                             minBufferSize << 1;
             this.underRunCallback = underRunCallback != null ? underRunCallback : (int samplesRequested) -> {};
             xAudioJSVolume = volume >= 0 && volume <= 1 ? volume : 1;
             this.initializeAudio();
         }
         public void callbackBasedWriteAudioNoCallback(ArrayList<Integer> buffer) {
             // Callback-centered audio APIs:
             int length = buffer.size();
             int bufferCounter = 0;
             while (bufferCounter < length && audioBufferSize < webAudioMaxBufferSize) {
                 audioContextSampleBuffer.set(audioBufferSize++, buffer.get(bufferCounter++));
             }
         }
         /*Pass your samples into here if you don't want automatic callback calling:
         Pack your samples as a one-dimenional array
         With the channel samplea packed uniformly.
         examples:
         mono - [left, left, left, left]
         stereo - [left, right, left, right, left, right, left, right]
         Useful in preventing infinite recursion issues with calling writeAudio inside your callback.
         */
         public void writeAudioNoCallback(ArrayList<Integer> buffer) {
             if (this.audioType == 0) {
             } else if (this.audioType == 1) {
                 this.callbackBasedWriteAudioNoCallback(buffer);
             } else if (this.audioType == GBEMU_2) {
                 if (this.checkFlashInit() || launchedContext) {
                     this.callbackBasedWriteAudioNoCallback(buffer);
                 } else if (this.mozAudioFound) {
                 }
             }
         }
         //Developer can use this to see how many samples to write (example: minimum buffer allotment minus remaining samples left returned from this function to make sure maximum buffering is done...)
         //If -1 is returned, then that means metric could not be done.
         public int remainingBuffer() {
             if (this.audioType == 0) {
                 //mozAudio:
             } else if (this.audioType == 1) {
                 //WebKit Audio:
                 return (((int) (resampledSamplesLeft() * resampleControl.ratioWeight) >> (this.audioChannels - 1)) << (this.audioChannels - 1)) + audioBufferSize;
             } else if (this.audioType == GBEMU_2) {
                 if (this.checkFlashInit() || launchedContext) {
                     //Webkit Audio / Flash Plugin Audio:
                     return (((int) (resampledSamplesLeft() * resampleControl.ratioWeight) >> (this.audioChannels - 1)) << (this.audioChannels - 1)) + audioBufferSize;
                 } else if (this.mozAudioFound) {
                     //mozAudio:
                 }
             }
             //Default return:
             return 0;
         }
         //DO NOT CALL THIS, the lib calls this internally!
         public void initializeAudio() {
             if (launchedContext) {
                 this.initializeWebAudio();
             } else {
                 this.initializeFlashAudio();
             }
         }
         public void initializeWebAudio() {
             resetCallbackAPIAudioBuffer(webAudioActualSampleRate, samplesPerCallback);
             this.audioType = 1;
         }
         public void changeVolume(int newVolume) {
             if (newVolume >= 0 && newVolume <= 1) {
                 xAudioJSVolume = newVolume;
                 if (this.checkFlashInit()) {
                 }
             }
         }
         public void initializeFlashAudio() {}
         //Checks to see if the NPAPI Adobe Flash bridge is ready yet:
         public boolean checkFlashInit() {
             return this.flashInitialized;
         }
     }
 
     public static class Audio { }
 
     /////////END LIB
     public static ArrayList<Integer> getFloat32(int size) {
         return new ArrayList<Integer>(Collections.nCopies(size, 0));
     }
     public static ArrayList<Integer> getFloat32Flat(int size) {
         return new ArrayList<Integer>(Collections.nCopies(size, 0));
     }
     //Flash NPAPI Event Handler:
     public static int samplesPerCallback = 2048;//Has to be between 2048 and 4096 (If over, then samples are ignored, if under then silence is added).
     public static GbemuPartGenerateFlash outputConvert = null;
     public static String generateFlashStereoString(){
         //Convert the arrays to one long string for speed.
         String copyBinaryStringLeft = "";
         String copyBinaryStringRight = "";
         int index = 0;
         while (index < samplesPerCallback && resampleBufferStart != resampleBufferEnd) {
             //Sanitize the buffer:
             copyBinaryStringLeft += Character.toString((char) (((int) (Math.min(Math.max(resampled.get(resampleBufferStart++) + 1, 0), GBEMU_2) * GBEMU_0x3FFF) | 0) + GBEMU_0x3000));
             copyBinaryStringRight += Character.toString((char) (((int) (Math.min(Math.max(resampled.get(resampleBufferStart++) + 1, 0), GBEMU_2) * GBEMU_0x3FFF) | 0) + GBEMU_0x3000));
             if (resampleBufferStart == resampleBufferSize) {
                 resampleBufferStart = 0;
             }
             index += 1;
         }
         return copyBinaryStringLeft + copyBinaryStringRight;
     }
     public static String generateFlashMonoString() {
         //Convert the array to one long string for speed.
         String copyBinaryString = "";
         int index = 0;
         while (index < samplesPerCallback && resampleBufferStart != resampleBufferEnd) {
             //Sanitize the buffer:
             copyBinaryString += Character.toString((char) ((((int) Math.min(Math.max(resampled.get(resampleBufferStart++) + 1, 0), GBEMU_2) * GBEMU_0x3FFF) | 0) + GBEMU_0x3000));
             if (resampleBufferStart == resampleBufferSize) {
                 resampleBufferStart = 0;
             }
             index += 1;
         }
         return copyBinaryString;
     };
 
     // Audio API Event Handler:
     public static GameBoyAudioContext audioContextHandle = null;
     public static GameBoyAudioNodeConstrc audioNode = null;
     public static GameBoyAudioContextBufferSource audioSource = null;
     public static boolean launchedContext = false;
     public static ArrayList<Integer> audioContextSampleBuffer = new ArrayList<>(Collections.nCopies(62914, 0));
     public static ArrayList<Integer> resampled = new ArrayList<>();
     public static int webAudioMinBufferSize = GBEMU_15000;
     public static int webAudioMaxBufferSize = GBEMU_250000;
     public static int webAudioActualSampleRate = GBEMU_44100;
     public static int xAudioJSSampleRate = 0;
     public static boolean webAudioMono = false;
     public static int xAudioJSVolume = 1;
     public static Resampler resampleControl = null;
     public static int audioBufferSize = 0;
     public static int resampleBufferStart = 0;
     public static int resampleBufferEnd = 0;
     public static int resampleBufferSize = GBEMU_2;
 
     public static void audioOutputEvent(GameBoyAudioNodeEvent event) {
         //Web Audio API callback...
         int index = 0;
         Integer[] buffer1 = event.outputBuffer.getChannelData(0);
         Integer[] buffer2 = event.outputBuffer.getChannelData(1);
         resampleRefill();
         if (!webAudioMono) {
             //STEREO:
             while (index < samplesPerCallback && resampleBufferStart != resampleBufferEnd) {
                 buffer1[index] = resampled.get(resampleBufferStart++) * xAudioJSVolume;
                 buffer2[index++] = resampled.get(resampleBufferStart++) * xAudioJSVolume;
                 if (resampleBufferStart == resampleBufferSize) {
                     resampleBufferStart = 0;
                 }
             }
         } else {
             //MONO:
             while (index < samplesPerCallback && resampleBufferStart != resampleBufferEnd) {
                 buffer1[index] = resampled.get(resampleBufferStart++) * xAudioJSVolume;
                 buffer2[index] = buffer1[index];
                 index += 1;
                 if (resampleBufferStart == resampleBufferSize) {
                     resampleBufferStart = 0;
                 }
             }
         }
         //Pad with silence if we're underrunning:
         while (index < samplesPerCallback) {
             buffer1[index] = 0;
             buffer2[index] = 0;
             index += 1;
         }
     };
 
     public static void resampleRefill() {
         if (audioBufferSize > 0) {
             //Resample a chunk of audio:
             int resampleLength =  (int) resampleControl.resampler.call(getBufferSamples());
             ArrayList<Integer> resampledResult = resampleControl.outputBuffer;
             for (int index2 = 0; index2 < resampleLength; ++index2) {
                 resampled.set(resampleBufferEnd++, resampledResult.get(index2));
                 if (resampleBufferEnd == resampleBufferSize) {
                     resampleBufferEnd = 0;
                 }
                 if (resampleBufferStart == resampleBufferEnd) {
                     resampleBufferStart += 1;
                     if (resampleBufferStart == resampleBufferSize) {
                         resampleBufferStart = 0;
                     }
                 }
             }
             audioBufferSize = 0;
         }
     }
 
     public static int resampledSamplesLeft() {
         return (resampleBufferStart <= resampleBufferEnd ? 0 : resampleBufferSize) + resampleBufferEnd - resampleBufferStart;
     }
 
     public static ArrayList<Integer> getBufferSamples() {
         // Typed array and normal array buffer section referencing:
         return new ArrayList<Integer>(audioContextSampleBuffer.subList(0, audioBufferSize));
     }
 
     //Initialize WebKit Audio /Flash Audio Buffer:
     public static void resetCallbackAPIAudioBuffer(int APISampleRate, int bufferAlloc) {
         audioContextSampleBuffer = getFloat32(webAudioMaxBufferSize);
         audioBufferSize = webAudioMaxBufferSize;
         resampleBufferStart = 0;
         resampleBufferEnd = 0;
         resampleBufferSize = (int) Math.max(webAudioMaxBufferSize * Math.ceil(xAudioJSSampleRate / APISampleRate), samplesPerCallback) << 1;
         if (webAudioMono) {
             //MONO Handling:
             resampled = getFloat32Flat(resampleBufferSize);
             resampleControl = new Resampler(xAudioJSSampleRate, APISampleRate, 1, resampleBufferSize, true);
             outputConvert = Gbemu::generateFlashMonoString;
         } else {
             //STEREO Handling:
             resampleBufferSize <<= 1;
             resampled = getFloat32Flat(resampleBufferSize);
             resampleControl = new Resampler(xAudioJSSampleRate, APISampleRate, GBEMU_2, resampleBufferSize, true);
             outputConvert = Gbemu::generateFlashStereoString;
         }
     }
 
     //Initialize WebKit Audio:
     public static void initializeWebKitAudio() {
         debugLog("This is initializeWebKitAudio");
         if (!launchedContext) {
             // The following line was modified for benchmarking:
             audioContextHandle = new GameBoyAudioContext(); //Create a system audio context.
             audioSource = audioContextHandle.createBufferSource(); //We need to create a false input to get the chain started.
             audioSource.loop = false; //Keep this alive forever (Event handler will know when to ouput.)
             xAudioJSSampleRate = audioContextHandle.sampleRate;
             webAudioActualSampleRate = audioContextHandle.sampleRate;
             audioSource.buffer = audioContextHandle.createBuffer(1, 1, webAudioActualSampleRate); //Create a zero'd input buffer for the input to be valid.
             audioNode = audioContextHandle.createJavaScriptNode(samplesPerCallback, 1, GBEMU_2); //Create GBEMU_2 outputs and ignore the input buffer (Just copy buffer 1 over if mono)
             audioNode.onaudioprocess = Gbemu::audioOutputEvent; //Connect the audio processing event to a handling function so we can manipulate output
             audioSource.connect(audioNode); //Send and chain the input to the audio manipulation.
             audioNode.connect(audioContextHandle.destination); //Send and chain the output of the audio manipulation to the system audio output.
             audioSource.noteOn(0); //Start the loop!
             launchedContext = true;
         }
     }
 // End of js/other/XAudioServer.js file.
 
 // Start of js/other/resize.js file.
 
     //JavaScript Image Resizer (c) 2012 - Grant Galitz
     public static class Resize {
         public static int widthOriginal = 0;
         public static int heightOriginal = 0;
         public static int targetWidth = 0;
         public static int targetHeight = 0;
         public static boolean blendAlpha = false;
         public static int colorChannels = 0;
         public static boolean interpolationPass = false;
         public static int targetWidthMultipliedByChannels = 0;
         public static int originalWidthMultipliedByChannels = 0;
         public static int originalHeightMultipliedByChannels = 0;
         public static int widthPassResultSize = 0;
         public static int finalResultSize = 0;
         public static GbemuPartResizeHeightAndWidth resizeWidth = null;
         public static GbemuPartResizeHeightAndWidth resizeHeight = null;
         public static int ratioWeightWidthPass = 0;
         public static int ratioWeightHeightPass = 0;
         public static ArrayList<Integer> outputWidthWorkBench = new ArrayList<>();
         public static ArrayList<Integer> widthBuffer = new ArrayList<>();
         public static ArrayList<Integer> outputHeightWorkBench = new ArrayList<>();
         public static ArrayList<Integer> heightBuffer = new ArrayList<>();
         Resize(int widthOriginal, int heightOriginal, int targetWidth, int targetHeight, boolean blendAlpha, boolean interpolationPass) {
             this.blendAlpha = blendAlpha;
             this.widthOriginal = Math.abs(Integer.parseInt(String.valueOf(widthOriginal)));
             this.heightOriginal = Math.abs(Integer.parseInt(String.valueOf(heightOriginal)));
             this.targetWidth = Math.abs(Integer.parseInt(String.valueOf(targetWidth)));
             this.targetHeight = Math.abs(Integer.parseInt(String.valueOf(targetHeight)));
             this.colorChannels = blendAlpha ? GBEMU_4 : GBEMU_3;
             this.interpolationPass = interpolationPass;
             this.targetWidthMultipliedByChannels = this.targetWidth * this.colorChannels;
             this.originalWidthMultipliedByChannels = this.widthOriginal * this.colorChannels;
             this.originalHeightMultipliedByChannels = this.heightOriginal * this.colorChannels;
             this.widthPassResultSize = this.targetWidthMultipliedByChannels * this.heightOriginal;
             this.finalResultSize = this.targetWidthMultipliedByChannels * this.targetHeight;
             this.initialize();
         }
 
         public void initialize() {
             //Perform some checks:
             if (this.widthOriginal > 0 && this.heightOriginal > 0 && this.targetWidth > 0 && this.targetHeight > 0) {
                 if (this.widthOriginal == this.targetWidth) {
                     //Bypass the width resizer pass:
                     this.resizeWidth = Resize::bypassResizer;
                 } else {
                     //Setup the width resizer pass:
                     this.ratioWeightWidthPass = this.widthOriginal / this.targetWidth;
                     if (this.ratioWeightWidthPass < 1 && this.interpolationPass) {
                         this.initializeFirstPassBuffers(true);
                         this.resizeWidth = this.colorChannels == GBEMU_4 ? Resize::resizeWidthInterpolatedRGBA : Resize::resizeWidthInterpolatedRGB;
                     } else {
                         this.initializeFirstPassBuffers(false);
                         this.resizeWidth = this.colorChannels == GBEMU_4 ? Resize::resizeWidthRGBA : Resize::resizeWidthRGB;
                     }
                 }
                 if (this.heightOriginal == this.targetHeight) {
                     //Bypass the height resizer pass:
                     this.resizeHeight = Resize::bypassResizer;
                 } else {
                     //Setup the height resizer pass:
                     this.ratioWeightHeightPass = this.heightOriginal / this.targetHeight;
                     if (this.ratioWeightHeightPass < 1 && this.interpolationPass) {
                         this.initializeSecondPassBuffers(true);
                         this.resizeHeight = Resize::resizeHeightInterpolated;
                     } else {
                         this.initializeSecondPassBuffers(false);
                         this.resizeHeight = this.colorChannels == GBEMU_4 ? Resize::resizeHeightRGBA : Resize::resizeHeightRGB;
                     }
                 }
             }
         }
 
         public static ArrayList<Integer> resizeWidthRGB(ArrayList<Integer> buffer) {
             int ratioWeight = ratioWeightWidthPass;
             int weight = 0;
             int amountToNext = 0;
             int actualPosition = 0;
             int currentPosition = 0;
             int line = 0;
             int pixelOffset = 0;
             int outputOffset = 0;
             int nextLineOffsetOriginalWidth = originalWidthMultipliedByChannels - GBEMU_2;
             int nextLineOffsetTargetWidth = targetWidthMultipliedByChannels - GBEMU_2;
             ArrayList<Integer> output = outputWidthWorkBench;
             ArrayList<Integer> outputBuffer = widthBuffer;
             do {
                 line = 0;
                 while (line < originalHeightMultipliedByChannels) {
                     output.set(line++,  0);
                     output.set(line++,  0);
                     output.set(line++,  0);
                 }
                 weight = ratioWeight;
                 do {
                     amountToNext = 1 + actualPosition - currentPosition;
                     if (weight >= amountToNext) {
                         line = 0;
                         pixelOffset = actualPosition;
                         while (line < originalHeightMultipliedByChannels) {
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * amountToNext);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * amountToNext);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset) * amountToNext);
                             pixelOffset += nextLineOffsetOriginalWidth;
                         }
                         actualPosition = actualPosition + GBEMU_3;
                         currentPosition = actualPosition;
                         weight -= amountToNext;
                     } else {
                         line = 0;
                         pixelOffset = actualPosition;
                         while (line < originalHeightMultipliedByChannels) {
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * weight);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * weight);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset) * weight);
                             pixelOffset += nextLineOffsetOriginalWidth;
                         }
                         currentPosition += weight;
                         break;
                     }
                 } while (weight > 0 && actualPosition < originalWidthMultipliedByChannels);
                 line = 0;
                 pixelOffset = outputOffset;
                 while (line < originalHeightMultipliedByChannels) {
                     outputBuffer.set(pixelOffset++, output.get(line++) / ratioWeight);
                     outputBuffer.set(pixelOffset++, output.get(line++) / ratioWeight);
                     outputBuffer.set(pixelOffset, output.get(line++) / ratioWeight);
                     pixelOffset += nextLineOffsetTargetWidth;
                 }
                 outputOffset += GBEMU_3;
             } while (outputOffset < targetWidthMultipliedByChannels);
             return outputBuffer;
         };
 
         public static ArrayList<Integer> resizeWidthInterpolatedRGB(ArrayList<Integer> buffer) {
             int ratioWeight = (widthOriginal - 1) / targetWidth;
             int weight = 0;
             int finalOffset = 0;
             int pixelOffset = 0;
             ArrayList<Integer> outputBuffer = widthBuffer;
             int targetPosition = 0;
             while (targetPosition < targetWidthMultipliedByChannels) {
                 //Calculate weightings:
                 int secondWeight = weight % 1;
                 int firstWeight = 1 - secondWeight;
                 //Interpolate:
                 finalOffset = targetPosition;
                 pixelOffset = ((int) Math.floor(weight)) * GBEMU_3;
                 while (finalOffset < widthPassResultSize) {
                     outputBuffer.set(finalOffset, buffer.get(pixelOffset) * firstWeight + buffer.get(pixelOffset + GBEMU_3) * secondWeight);
                     outputBuffer.set(finalOffset + 1, buffer.get(pixelOffset + 1) * firstWeight + buffer.get(pixelOffset + GBEMU_4) * secondWeight);
                     outputBuffer.set(finalOffset + GBEMU_2, buffer.get(pixelOffset + GBEMU_2) * firstWeight + buffer.get(pixelOffset + GBEMU_5) * secondWeight);
                     pixelOffset += originalWidthMultipliedByChannels;
                     finalOffset += targetWidthMultipliedByChannels;
                 }
                 targetPosition += GBEMU_3;
                 weight += ratioWeight;
             }
             return outputBuffer;
         };
 
         public static ArrayList<Integer> resizeWidthInterpolatedRGBA(ArrayList<Integer> buffer){
             int ratioWeight = (widthOriginal - 1) / targetWidth;
             int weight = 0;
             int finalOffset = 0;
             int pixelOffset = 0;
             ArrayList<Integer> outputBuffer = widthBuffer;
             int targetPosition = 0;
             while (targetPosition < targetWidthMultipliedByChannels) {
                 //Calculate weightings:
                 int secondWeight = weight % 1;
                 int firstWeight = 1 - secondWeight;
                 //Interpolate:
                 finalOffset = targetPosition;
                 pixelOffset = (int) (Math.floor(weight) * GBEMU_4);
                 while (finalOffset < widthPassResultSize) {
                     outputBuffer.set(finalOffset, ( buffer.get(pixelOffset) * firstWeight + buffer.get(pixelOffset + GBEMU_4) * secondWeight));
                     outputBuffer.set(finalOffset + 1, ( buffer.get(pixelOffset + 1) * firstWeight + buffer.get(pixelOffset + GBEMU_5) * secondWeight));
                     outputBuffer.set(finalOffset + GBEMU_2, ( buffer.get(pixelOffset + GBEMU_2) * firstWeight + buffer.get(pixelOffset + GBEMU_6) * secondWeight));
                     outputBuffer.set(finalOffset + GBEMU_3, ( buffer.get(pixelOffset + GBEMU_3) * firstWeight + buffer.get(pixelOffset + GBEMU_7) * secondWeight));
                     pixelOffset += originalWidthMultipliedByChannels;
                     finalOffset += targetWidthMultipliedByChannels;
                 }
                 targetPosition += GBEMU_4;
                 weight += ratioWeight;
             }
             return outputBuffer;
         };
 
         public static ArrayList<Integer> resizeWidthRGBA(ArrayList<Integer> buffer) {
             int ratioWeight = ratioWeightWidthPass;
             int weight = 0;
             int amountToNext = 0;
             int actualPosition = 0;
             int currentPosition = 0;
             int line = 0;
             int pixelOffset = 0;
             int outputOffset = 0;
             int nextLineOffsetOriginalWidth = originalWidthMultipliedByChannels - GBEMU_3;
             int nextLineOffsetTargetWidth = targetWidthMultipliedByChannels - GBEMU_3;
             ArrayList<Integer> output = outputWidthWorkBench;
             ArrayList<Integer> outputBuffer = widthBuffer;
             do {
                 line = 0;
                 while (line < originalHeightMultipliedByChannels) {
                     output.set(line++,  0);
                     output.set(line++,  0);
                     output.set(line++,  0);
                     output.set(line++,  0);
                 }
                 weight = ratioWeight;
                 do {
                     amountToNext = 1 + actualPosition - currentPosition;
                     if (weight >= amountToNext) {
                         line = 0;
                         pixelOffset = actualPosition;
                         while (line < originalHeightMultipliedByChannels) {
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * amountToNext);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * amountToNext);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * amountToNext);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset) * amountToNext);
                             pixelOffset += nextLineOffsetOriginalWidth;
                         }
                         actualPosition = actualPosition + GBEMU_4;
                         currentPosition = actualPosition;
                         weight -= amountToNext;
                     } else {
                         line = 0;
                         pixelOffset = actualPosition;
                         while (line < originalHeightMultipliedByChannels) {
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * weight);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * weight);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset++) * weight);
                             output.set(line++, output.get(line++) + buffer.get(pixelOffset) * weight);
                             pixelOffset += nextLineOffsetOriginalWidth;
                         }
                         currentPosition += weight;
                         break;
                     }
                 } while (weight > 0 && actualPosition < originalWidthMultipliedByChannels);
                 line = 0;
                 pixelOffset = outputOffset;
                 while (line < originalHeightMultipliedByChannels) {
                     outputBuffer.set(pixelOffset++, output.get(line++) / ratioWeight);
                     outputBuffer.set(pixelOffset++, output.get(line++) / ratioWeight);
                     outputBuffer.set(pixelOffset++, output.get(line++) / ratioWeight);
                     outputBuffer.set(pixelOffset, output.get(line++) / ratioWeight);
                     pixelOffset += nextLineOffsetTargetWidth;
                 }
                 outputOffset += GBEMU_4;
             } while (outputOffset < targetWidthMultipliedByChannels);
             return outputBuffer;
         };
 
         public static ArrayList<Integer> resizeHeightRGB(ArrayList<Integer> buffer) {
             int ratioWeight = ratioWeightHeightPass;
             int weight = 0;
             int amountToNext = 0;
             int actualPosition = 0;
             int currentPosition = 0;
             int pixelOffset = 0;
             int outputOffset = 0;
             ArrayList<Integer> output = outputHeightWorkBench;
             ArrayList<Integer> outputBuffer = heightBuffer;
             do {
                 pixelOffset = 0;
                 while (pixelOffset < targetWidthMultipliedByChannels) {
                     output.set(pixelOffset++, 0);
                     output.set(pixelOffset++, 0);
                     output.set(pixelOffset++, 0);
                 }
                 weight = ratioWeight;
                 do {
                     amountToNext = 1 + actualPosition - currentPosition;
                     if (weight >= amountToNext) {
                         pixelOffset = 0;
                         while (pixelOffset < targetWidthMultipliedByChannels) {
                             output.set(pixelOffset++, output.get(pixelOffset++) + (buffer.get(actualPosition++)) * amountToNext);
                             output.set(pixelOffset++, output.get(pixelOffset++) + (buffer.get(actualPosition++)) * amountToNext);
                             output.set(pixelOffset++, output.get(pixelOffset++) + (buffer.get(actualPosition++)) * amountToNext);
                         }
                         currentPosition = actualPosition;
                         weight -= amountToNext;
                     } else {
                         pixelOffset = 0;
                         amountToNext = actualPosition;
                         while (pixelOffset < targetWidthMultipliedByChannels) {
                             output.set(pixelOffset++, output.get(pixelOffset++) + (buffer.get(amountToNext++)) * weight);
                             output.set(pixelOffset++, output.get(pixelOffset++) + (buffer.get(amountToNext++)) * weight);
                             output.set(pixelOffset++, output.get(pixelOffset++) + (buffer.get(amountToNext++)) * weight);
                         }
                         currentPosition += weight;
                         break;
                     }
                 } while (weight > 0 && actualPosition < widthPassResultSize);
                 pixelOffset = 0;
                 while (pixelOffset < targetWidthMultipliedByChannels) {
                     outputBuffer.set(outputOffset++,  Math.round(output.get(pixelOffset++) / ratioWeight));
                     outputBuffer.set(outputOffset++,  Math.round(output.get(pixelOffset++) / ratioWeight));
                     outputBuffer.set(outputOffset++,  Math.round(output.get(pixelOffset++) / ratioWeight));
                 }
             } while (outputOffset < finalResultSize);
             return outputBuffer;
         };
 
         public static ArrayList<Integer> resizeHeightInterpolated(ArrayList<Integer> buffer) {
             int ratioWeight = (heightOriginal - 1) / targetHeight;
             int weight = 0;
             int finalOffset = 0;
             int pixelOffset = 0;
             int pixelOffsetAccumulated = 0;
             int pixelOffsetAccumulated2 = 0;
             ArrayList<Integer> outputBuffer = heightBuffer;
             do {
                 //Calculate weightings:
                 int secondWeight = weight % 1;
                 int firstWeight = 1 - secondWeight;
                 //Interpolate:
                 pixelOffsetAccumulated = ((int) Math.floor(weight)) * targetWidthMultipliedByChannels;
                 pixelOffsetAccumulated2 = pixelOffsetAccumulated + targetWidthMultipliedByChannels;
                 pixelOffset = 0;
                 while (pixelOffset < targetWidthMultipliedByChannels) {
                     outputBuffer.set(
                             finalOffset++, buffer.get(pixelOffsetAccumulated + pixelOffset) * firstWeight + buffer.get(pixelOffsetAccumulated2 + pixelOffset) * secondWeight);
                     pixelOffset += 1;
                 }
                 weight += ratioWeight;
             } while (finalOffset < finalResultSize);
             return outputBuffer;
         };
 
         public static ArrayList<Integer> resizeHeightRGBA(ArrayList<Integer> buffer){
             int ratioWeight = ratioWeightHeightPass;
             int weight = 0;
             int amountToNext = 0;
             int actualPosition = 0;
             int currentPosition = 0;
             int pixelOffset = 0;
             int outputOffset = 0;
             ArrayList<Integer> output = outputHeightWorkBench;
             ArrayList<Integer> outputBuffer = heightBuffer;
             do {
                 pixelOffset = 0;
                 while (pixelOffset < targetWidthMultipliedByChannels) {
                     output.set(pixelOffset++, 0);
                     output.set(pixelOffset++, 0);
                     output.set(pixelOffset++, 0);
                     output.set(pixelOffset++, 0);
                 }
                 weight = ratioWeight;
                 do {
                     amountToNext = 1 + actualPosition - currentPosition;
                     if (weight >= amountToNext) {
                         pixelOffset = 0;
                         while (pixelOffset < targetWidthMultipliedByChannels) {
                             output.set(pixelOffset++, output.get(pixelOffset++) + buffer.get(actualPosition++) * amountToNext);
                             output.set(pixelOffset++, output.get(pixelOffset++) + buffer.get(actualPosition++) * amountToNext);
                             output.set(pixelOffset++, output.get(pixelOffset++) + buffer.get(actualPosition++) * amountToNext);
                             output.set(pixelOffset++, output.get(pixelOffset++) + buffer.get(actualPosition++) * amountToNext);
                         }
                         currentPosition = actualPosition;
                         weight -= amountToNext;
                     } else {
                         pixelOffset = 0;
                         amountToNext = actualPosition;
                         while (pixelOffset < targetWidthMultipliedByChannels) {
                             output.set(pixelOffset++, output.get(pixelOffset++) + buffer.get(amountToNext++) * weight);
                             output.set(pixelOffset++, output.get(pixelOffset++) + buffer.get(amountToNext++) * weight);
                             output.set(pixelOffset++, output.get(pixelOffset++) + buffer.get(amountToNext++) * weight);
                             output.set(pixelOffset++, output.get(pixelOffset++) + buffer.get(amountToNext++) * weight);
                         }
                         currentPosition += weight;
                         break;
                     }
                 } while (weight > 0 && actualPosition < widthPassResultSize);
                 pixelOffset = 0;
                 while (pixelOffset < targetWidthMultipliedByChannels) {
                     outputBuffer.set(outputOffset++,  Math.round(output.get(pixelOffset++) / ratioWeight));
                     outputBuffer.set(outputOffset++,  Math.round(output.get(pixelOffset++) / ratioWeight));
                     outputBuffer.set(outputOffset++,  Math.round(output.get(pixelOffset++) / ratioWeight));
                     outputBuffer.set(outputOffset++,  Math.round(output.get(pixelOffset++) / ratioWeight));
                 }
             } while (outputOffset < finalResultSize);
             return outputBuffer;
         };
 
         ArrayList<Integer> resize(ArrayList<Integer> buffer) {
             return this.resizeHeight.call(this.resizeWidth.call(buffer));
         }
 
         public static ArrayList<Integer> bypassResizer(ArrayList<Integer> buffer) {
             //Just return the buffer passsed:
             return buffer;
         };
 
         public void initializeFirstPassBuffers(boolean biLINEARAlgo) {
             //Initialize the internal width pass buffers:
             this.widthBuffer = this.generateFloatBuffer(this.widthPassResultSize);
             if (!biLINEARAlgo) {
                 this.outputWidthWorkBench = this.generateFloatBuffer(this.originalHeightMultipliedByChannels);
             }
         }
 
         public void initializeSecondPassBuffers(boolean biLINEARAlgo) {
             //Initialize the internal height pass buffers:
             this.heightBuffer = this.generateUint8Buffer(this.finalResultSize);
             if (!biLINEARAlgo) {
                 this.outputHeightWorkBench = this.generateFloatBuffer(this.targetWidthMultipliedByChannels);
             }
         }
 
         public ArrayList<Integer> generateFloatBuffer(int bufferLength) {
             //Generate a float32 typed array buffer:
             return new ArrayList(bufferLength);
         }
 
         public ArrayList<Integer> generateUint8Buffer(int bufferLength) {
             //Generate a uint8 typed array buffer:
             return new ArrayList(bufferLength);
         }
     }
 // End of js/other/resize.js file.
 
 // Remaining files are in gbemu-part2.js, since they run in strict mode.
 
     // ------ gbemu-part2 ------
     public static class GameBoyCore {
         // Params, etc...
         public GameBoyCanvas canvas = null; // Canvas DOM object for drawing out the graphics to.
         public Object drawContext = null; // LCD Context
         public String romImage = ""; // The game's rom.
        // CPU Registers and Flags:
         public int registerA = GBEMU_0x01; // Register A (Accumulator)
         public boolean fZero = true; // Register F - Result was zero
         public boolean fSubtract = false; // Register F - Subtraction was executed
         public boolean fHalfCarry = true; // Register F - Half carry or half borrow
         public boolean fCarry = true; // Register F - Carry or borrow
         public int registerB = GBEMU_0x00; // Register B
         public int registerC = GBEMU_0x13; // Register C
         public int registerD = GBEMU_0x00; // Register D
         public int registerE = GBEMU_0xD8; // Register E
         public int registerF = 0; // Register F
         public int registersHL = GBEMU_0x014D; // Registers H and L combined
         public int stackPointer = GBEMU_0xFFFE; // Stack Pointer
         public int programCounter = GBEMU_0x0100; // Program Counter
        // Some CPU Emulation State Variables:
         public int cpuCyclesTotal = 0; // Relative CPU clocking to speed set, rounded appropriately.
         public int cpuCyclesTotalBase = 0; // Relative CPU clocking to speed set base.
         public int cpuCyclesTotalCurrent = 0; // Relative CPU clocking to speed set, the directly used value.
         public double cpuCyclesTotalRoundoff = 0; // Clocking per iteration rounding catch.
         public double baseCPUCyclesPerIteration = 0; // CPU clocks per iteration at 1x speed.
         public int remainingClocks = 0; // HALT clocking overrun carry over.
         public boolean inBootstrap = true; // Whether we're in the GBC boot rom.
         public boolean usedBootrom = false; // Updated upon rom loading...
         public boolean usedGBCBootrom = false; // Did we boot to the GBC boot rom?
         public boolean halt = false; // Has the CPU been suspended until the next interrupt?
         public boolean skipPCIncrement = false; // Did we trip the DMG Halt bug?
         public int stopEmulator = GBEMU_3; // Has the emulation been paused or a frame has ended?
         public boolean ime = true; // Are interrupts enabled?
         public int irqLineMatched = 0; // CPU IRQ assertion.
         public int interruptsRequested = 0; // IF Register
         public int interruptsEnabled = 0; // IE Register
         public boolean hdmaRunning = false; // HDMA Transfer Flag - GBC only
         public int cpuTicks = 0; // The number of clock cycles emulated.
         public int doubleSpeedShifter = 0; // GBC double speed clocking shifter.
         public int joyPad = GBEMU_0xFF; // Joypad State (two four-bit states actually)
         public boolean cpuStopped = false; // CPU STOP status.
         // Main RAM, MBC RAM, GBC Main RAM, vram, etc.
         public static ArrayList<GbemuPartMemoryReaderOrHighReader> memoryReader = new ArrayList<>(Collections.nCopies(0xFFFF+1, (GameBoyCore parentObj, int address) -> { return 0; })); // Array of functions mapped to read back memory
         public static ArrayList<GbemuPartMemoryWriterOrHighWriter> memoryWriter = new ArrayList<>(Collections.nCopies(0xFFFF+1, (GameBoyCore parentObj, int address, int data) -> {})); // Array of functions mapped to write to memory
         public static ArrayList<GbemuPartMemoryReaderOrHighReader> memoryHighReader = new ArrayList<>(Collections.nCopies(0xFF+1, (GameBoyCore parentObj, int address) -> { return 0;})); // Array of functions mapped to read back 0xFFXX memory
         public static ArrayList<GbemuPartMemoryWriterOrHighWriter> memoryHighWriter = new ArrayList<>(Collections.nCopies(0xFF+1, (GameBoyCore parentObj, int address, int data) -> {}));  // Array of functions mapped to write to 0xFFXX memory
         public static ArrayList<Integer> rom = new ArrayList<>(); // The full rom file dumped to an array.
         public static ArrayList<Integer> memory = new ArrayList<>(); // Main Core Memory
         public static ArrayList<Integer> mbcRam = new ArrayList<>(); // Switchable RAM (Used by games for more RAM) for the main memory range 0xA000 - 0xC000.
         public static ArrayList<Integer> vram = new ArrayList<>(); // Extra vram bank for GBC.
         public static ArrayList<Integer> gbcMemory = new ArrayList<>(); // GBC main RAM Banks
         public static boolean mbc1Mode = false; // MBC1 Type (GBEMU_4/GBEMU_32, GBEMU_16/GBEMU_8)
         public static boolean mbcRamBanksEnabled = false; // MBC RAM Access Control.
         public static int currMBCRAMBank = 0; // MBC Currently Indexed RAM Bank
         public static int currMBCRAMBankPosition = -GBEMU_0xA000; // MBC Position Adder;
         public static boolean cGBC = false; // GameBoy Color detection.
         public static int gbcRamBank = 1; // Currently Switched GameBoy Color ram bank
         public static int gbcRamBankPosition = -GBEMU_0xD000; // GBC RAM offset from address start.
         public static int gbcRamBankPositionECHO = -GBEMU_0xF000; // GBC RAM (ECHO mirroring) offset from address start.
         public static int[] ramBanks = { 0, 1, GBEMU_2, GBEMU_4, GBEMU_16 }; // Used to map the RAM banks to maximum size the MBC used can do.
         public static int romBank1offs = 0; // Offset of the rom bank switching.
         public static int currentromBank = 0; // The parsed current rom bank selection.
         public static int cartridgeType = 0; // Cartridge Type
         public static String name = ""; // Name of the game
         public static String gameCode = ""; // Game code (Suffix for older games)
         public static boolean fromSaveState = false; // A boolean to see if this was loaded in as a save state.
         public static String savedStateFileName = ""; // When loaded in as a save state, this will not be empty.
         public static int statTracker = 0; // Tracker for STAT triggering.
         public int modeSTAT = 0; // The scan line mode (for lines 1-144 it's GBEMU_2-GBEMU_3-0, for 145-154 it's 1)
         public int spriteCount = GBEMU_252; // Mode GBEMU_3 extra clocking counter (Depends on how many sprites are on the current line.).
         public boolean lycMatchTriggerSTAT = false; // Should we trigger an interrupt if LY==LYC?
         public boolean mode2TriggerSTAT = false; // Should we trigger an interrupt if in mode GBEMU_2?
         public boolean mode1TriggerSTAT = false; // Should we trigger an interrupt if in mode 1?
         public boolean mode0TriggerSTAT = false; // Should we trigger an interrupt if in mode 0?
         public boolean lcdIsOn = false; // Is the emulated LCD controller on?
         public GbemuPartLCDControl[] lineControl = new GbemuPartLCDControl[154];
         public GbemuPartLCDControl[] disPlayOffControl = new GbemuPartLCDControl[]{
                 (parentObj) -> {
                     // Array of line 0 function to handle the LCD controller when it's off (Do nothing!).
                 }
         };
         public GbemuPartLCDControl[] lcdControl = new GbemuPartLCDControl[0]; // //Pointer to either lineControl or disPlayOffControl.
         // RTC (Real Time Clock for MBC3):
         public boolean rtcIsLatched = false;
         public int latchedSeconds = 0; // RTC latched seconds.
         public int latchedMinutes = 0; // RTC latched minutes.
         public int latchedHours = 0; // RTC latched hours.
         public int latchedLDays = 0; // RTC latched lower GBEMU_8-bits of the day counter.
         public int latchedHDays = 0; // RTC latched high-bit of the day counter.
         public int rtcSeconds = 0; // RTC seconds counter.
         public int rtcMinutes = 0; // RTC minutes counter.
         public int rtcHours = 0; // RTC hours counter.
         public int rtcDays = 0; // RTC days counter.
         public boolean rtcDayOverFlow = false; // Did the RTC overflow and wrap the day counter?
         public boolean rtcHalt = false; // Is the RTC allowed to clock up?
         // Gyro:
         public int highX = GBEMU_127;
         public int lowX = GBEMU_127;
         public int highY = GBEMU_127;
         public int lowY = GBEMU_127;
         // Sound variables:
         public XAudioServer audioHandle = null; // XAudioJS handle
         public int numSamplesTotal = 0; // Length of the sound buffers.
         public double sampleSize = 0; // Length of the sound buffer for one channel.
         public boolean[][] dutyLookup = {
                 // Map the duty values given to ones we can work with.
                 { false, false, false, false, false, false, false, true }, { true, false, false, false, false, false, false, true }, { true, false, false, false, false, true, true, true }, { false, true, true, true, true, true, true, false }
         };
         public ArrayList<Integer> currentBuffer = new ArrayList<>(); // The audio buffer we're working on.
         public ArrayList<Integer> secondaryBuffer = new ArrayList<>();
         public int bufferContainAmount = 0; // Buffer maintenance metric.
         public ArrayList<Integer> lsfr15Table = new ArrayList<>();
         public ArrayList<Integer> lsfr7Table = new ArrayList<>();
         public ArrayList<Integer> noiseSampleTable = new ArrayList<>();
 
         public boolean soundMasterEnabled = false; // As its name implies
         public ArrayList<Integer> channel3PCM = new ArrayList<>(); // Channel GBEMU_3 adjusted sample buffer.
         // Vin Shit:
         public int vinLeftChannelMasterVolume = GBEMU_8; // Computed post-mixing volume.
         public int vinRightChannelMasterVolume = GBEMU_8; // Computed post-mixing volume.
         // Channel paths enabled:
         public boolean leftChannel1 = false;
         public boolean leftChannel2 = false;
         public boolean leftChannel3 = false;
         public boolean leftChannel4 = false;
         public boolean rightChannel1 = false;
         public boolean rightChannel2 = false;
         public boolean rightChannel3 = false;
         public boolean rightChannel4 = false;
         // Channel output level caches:
         public int channel1currentSampleLeft = 0;
         public int channel1currentSampleRight = 0;
         public int channel2currentSampleLeft = 0;
         public int channel2currentSampleRight = 0;
         public int channel3currentSampleLeft = 0;
         public int channel3currentSampleRight = 0;
         public int channel4currentSampleLeft = 0;
         public int channel4currentSampleRight = 0;
         public int channel1currentSampleLeftSecondary = 0;
         public int channel1currentSampleRightSecondary = 0;
         public int channel2currentSampleLeftSecondary = 0;
         public int channel2currentSampleRightSecondary = 0;
         public int channel3currentSampleLeftSecondary = 0;
         public int channel3currentSampleRightSecondary = 0;
         public int channel4currentSampleLeftSecondary = 0;
         public int channel4currentSampleRightSecondary = 0;
         public int channel1currentSampleLeftTrimary = 0;
         public int channel1currentSampleRightTrimary = 0;
         public int channel2currentSampleLeftTrimary = 0;
         public int channel2currentSampleRightTrimary = 0;
         public int mixerOutputCache = 0;
         // Pre-multipliers to cache some calculations:
         public int machineOut = 0; // Premultiplier for audio samples per instruction.
         // Audio generation counters:
         public double audioTicks = 0; // Used to sample the audio system every x CPU instructions.
         public int audioIndex = 0; // Used to keep alignment on audio generation.
         public int rollover = 0; // Used to keep alignment on the number of samples to output (Realign from counter alias).
         // Timing Variables
         public int emulatorTicks = 0; // Times for how many instructions to execute before ending the loop.
         public int divTicks = GBEMU_56; // DIV Ticks Counter (Invisible lower GBEMU_8-bit)
         public int lcdTicks = GBEMU_60; // Counter for how many instructions have been executed on a scanline so far.
         public int timerTicks = 0; // Counter for the TIMA timer.
         public boolean timaEnabled = false; // Is TIMA enabled?
         public int tacClocker = GBEMU_1024; // Timer Max Ticks
         public int serialTimer = 0; // Serial IRQ Timer
         public int serialShiftTimer = 0; // Serial Transfer Shift Timer
         public int serialShiftTimerAllocated = 0; // Serial Transfer Shift Timer Refill
         public int irqEnableDelay = 0; // Are the interrupts on queue to be enabled?
         public int lastIteration = new NewDate().getTime(); // The last time we iterated the main loop.
         public int firstIteration = new NewDate().getTime(); // The line is changed for benchmarking.
         public int iterations = 0;
         public int actualScanLine = 0; // Actual scan line...
         public int lastUnrenderedLine = 0; // Last rendered scan line...
         public int queuedScanLines = 0;
         public int totalLinesPassed = 0;
         public int haltPostClocks = 0; // Post-Halt clocking.
         // rom Cartridge Components:
         public boolean cMBC1 = false; // Does the cartridge use MBC1?
         public boolean cMBC2 = false; // Does the cartridge use MBC2?
         public boolean cMBC3 = false; // Does the cartridge use MBC3?
         public boolean cMBC5 = false; // Does the cartridge use MBC5?
         public boolean cMBC7 = false; // Does the cartridge use MBC7?
         public boolean cSRAM = false; // Does the cartridge use save RAM?
         public boolean cMMMO1 = false; // ...
         public boolean cRUMBLE = false; // Does the cartridge use the RUMBLE addressing (modified MBC5)?
         public boolean cCamera = false; // Is the cartridge actually a GameBoy Camera?
         public boolean cTAMA5 = false; // Does the cartridge use TAMA5? (Tamagotchi Cartridge)
         public boolean cHuC3 = false; // Does the cartridge use HuC3 (Hudson Soft / modified MBC3)?
         public boolean cHuC1 = false; // Does the cartridge use HuC1 (Hudson Soft / modified MBC1)?
         public boolean cTimeR = false; // Does the cartridge have an RTC?
         public int romBanks[] = new int[] { 
         // 1 Bank = GBEMU_16 KBytes = 256 Kbits
                 GBEMU_2, GBEMU_4, GBEMU_8, GBEMU_16, GBEMU_32, GBEMU_64, GBEMU_128, GBEMU_256, GBEMU_512
         };
         public int numRamBanks = 0; // How many RAM banks were actually allocated?
         // Graphics Variables
         public static int currvramBank = 0; // Current vram bank for GBC.
         public static int backgroundX = 0; // Register SCX (X-Scroll)
         public static int backgroundY = 0; // Register SCY (Y-Scroll)
         public static boolean gfxWindowDisplay = false; // Is the windows enabled?
         public static boolean gfxSpriteShow = false; // Are sprites enabled?
         public static boolean gfxSpriteNormalHeight = true; // Are we doing 8x8 or 8x16 sprites?
         public static boolean bgEnabled = true; // Is the BG enabled?
         public static boolean bgPriorityEnabled = true; // Can we flag the BG for priority over sprites?
         public static int gfxWindowCHRBankPosition = 0; // The current bank of the character map the window uses.
         public static int gfxBackgroundCHRBankPosition = 0; // The current bank of the character map the BG uses.
         public static int gfxBackgroundBankOffset = GBEMU_0x80; // Fast mapping of the tile numbering/
         public static int windowY = 0; // Current Y offset of the window.
         public static int windowX = 0; // Current X offset of the window.
         public static int drewBlank = 0; // To prevent the repeating of drawing a blank screen.
         public static boolean drewFrame = false; // Throttle how many draws we can do to once per iteration.
         public static int midScanlineOffset = -1; // mid-scanline rendering offset.
         public static int pixelEnd = 0; // track the x-coord limit for line rendering (mid-scanline usage).
         public static int currentX = 0; // The x-coord we left off at for mid-scanline rendering.
         // BG Tile Pointer Caches:
         public static ArrayObject bgCHRBank1 = new ArrayObject();
         public static ArrayObject bgCHRBank2 = new ArrayObject();
         public static ArrayObject bgCHRCurrentBank = null;
         // Tile Data Cache:
         public static ArrayList<ArrayObject> tileCache = new ArrayList<>();
         // Palettes:
         public static int[] colors = { GBEMU_0xEFFFDE, GBEMU_0xADD794, GBEMU_0x529273, GBEMU_0x183442 }; // 'Classic' GameBoy palette colors.
         public static ArrayList<Integer> objPalette = new ArrayList<>();
         public static ArrayList<Integer> bgPalette = new ArrayList<>();
         public static ArrayList<Integer> gbcOBJRawPalette = new ArrayList<>();
         public static ArrayList<Integer> gbcBGRawPalette = new ArrayList<>();
         public static ArrayList<Integer> gbOBJPalette = new ArrayList<>();
         public static ArrayList<Integer> gbBGPalette = new ArrayList<>();
         public static ArrayList<Integer> gbcOBJPalette = new ArrayList<>();
         public static ArrayList<Integer> gbcBGPalette = new ArrayList<>();
         public static ArrayList<Integer> gbBGColorizedPalette = new ArrayList<>();
         public static ArrayList<Integer> gbOBJColorizedPalette = new ArrayList<>();
         public static ArrayList<Integer> cachedBGPaletteConversion = new ArrayList<>();
         public static ArrayList<Integer> cachedOBJPaletteConversion = new ArrayList<>();
         public static GbemuPartSingeParamInt updateGBBGPalette = null;
         public static GbemuPartGBOBJPalette updateGBOBJPalette = null;
         public static boolean colorizedGBPalettes = false;
         public static GbemuPartSingeParamInt bgLayerRender = null; // Reference to the BG rendering function.
         public static GbemuPartSingeParamInt windowLayerRender = null; // Reference to the window rendering function.
         public static GbemuPartSingeParamInt spriteLayerRender = null; // Reference to the OAM rendering function.
         public static ArrayList<Integer> frameBuffer = new ArrayList<>(); // The internal frame-buffer.
         public static ArrayList<Integer> swizzledFrame = new ArrayList<>(); // The secondary gfx buffer that holds the converted RGBA values.
         public static GameBoyContextImageDataResult canvasBuffer = null; // imageData handle
         public static int pixelStart = 0; // Temp variable for holding the current working framebuffer offset.
         // Variables used for scaling in JS:
         public static int onscreenWidth = GBEMU_160;
         public static int offscreenWidth = GBEMU_160;
         public static int onscreenHeight = GBEMU_144;
         public static int offscreenHeight = GBEMU_144;
         public static int offscreenRGBCount = onscreenWidth * onscreenHeight * GBEMU_4;
 
         // Start of code changed for benchmarking (removed rom):
         public static int[] gbBOOTrom = {};
         public static int[] gbCBOOTrom = {};
         // End of code changed for benchmarking.
 
         public static int[] ffxxDump = {
                 // Dump of the post-BOOT I/O register state (From gambatte):
                 GBEMU_0x0F, GBEMU_0x00, GBEMU_0x7C, GBEMU_0xFF, GBEMU_0x00, GBEMU_0x00, GBEMU_0x00, GBEMU_0xF8, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0x01, GBEMU_0x80, GBEMU_0xBF, GBEMU_0xF3, GBEMU_0xFF, GBEMU_0xBF, GBEMU_0xFF, GBEMU_0x3F, GBEMU_0x00, GBEMU_0xFF, GBEMU_0xBF, GBEMU_0x7F, GBEMU_0xFF, GBEMU_0x9F, GBEMU_0xFF, GBEMU_0xBF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0x00, GBEMU_0x00, GBEMU_0xBF, GBEMU_0x77, GBEMU_0xF3, GBEMU_0xF1, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x91, GBEMU_0x80, GBEMU_0x00, GBEMU_0x00, GBEMU_0x00, GBEMU_0x00, GBEMU_0x00, GBEMU_0xFC, GBEMU_0x00, GBEMU_0x00, GBEMU_0x00, GBEMU_0x00, GBEMU_0xFF, GBEMU_0x7E, GBEMU_0xFF, GBEMU_0xFE, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0x3E, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xC0, GBEMU_0xFF, GBEMU_0xC1, GBEMU_0x00, GBEMU_0xFE, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xF8, GBEMU_0xFF, GBEMU_0x00, GBEMU_0x00, GBEMU_0x00, GBEMU_0x8F, GBEMU_0x00, GBEMU_0x00, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xFF, GBEMU_0xCE, GBEMU_0xED, GBEMU_0x66, GBEMU_0x66, GBEMU_0xCC, GBEMU_0x0D, GBEMU_0x00, GBEMU_0x0B, GBEMU_0x03, GBEMU_0x73, GBEMU_0x00, GBEMU_0x83, GBEMU_0x00, GBEMU_0x0C, GBEMU_0x00, GBEMU_0x0D, GBEMU_0x00, GBEMU_0x08, GBEMU_0x11, GBEMU_0x1F, GBEMU_0x88, GBEMU_0x89, GBEMU_0x00, GBEMU_0x0E, GBEMU_0xDC, GBEMU_0xCC, GBEMU_0x6E, GBEMU_0xE6, GBEMU_0xDD, GBEMU_0xDD, GBEMU_0xD9, GBEMU_0x99, GBEMU_0xBB, GBEMU_0xBB, GBEMU_0x67, GBEMU_0x63, GBEMU_0x6E, GBEMU_0x0E, GBEMU_0xEC, GBEMU_0xCC, GBEMU_0xDD, GBEMU_0xDC, GBEMU_0x99, GBEMU_0x9F, GBEMU_0xBB, GBEMU_0xB9, GBEMU_0x33, GBEMU_0x3E, GBEMU_0x45, GBEMU_0xEC, GBEMU_0x52, GBEMU_0xFA, GBEMU_0x08, GBEMU_0xB7, GBEMU_0x07, GBEMU_0x5D, GBEMU_0x01, GBEMU_0xFD, GBEMU_0xC0, GBEMU_0xFF, GBEMU_0x08, GBEMU_0xFC, GBEMU_0x00, GBEMU_0xE5, GBEMU_0x0B, GBEMU_0xF8, GBEMU_0xC2, GBEMU_0xCE, GBEMU_0xF4, GBEMU_0xF9, GBEMU_0x0F, GBEMU_0x7F, GBEMU_0x45, GBEMU_0x6D, GBEMU_0x3D, GBEMU_0xFE, GBEMU_0x46, GBEMU_0x97, GBEMU_0x33, GBEMU_0x5E, GBEMU_0x08, GBEMU_0xEF, GBEMU_0xF1, GBEMU_0xFF, GBEMU_0x86, GBEMU_0x83, GBEMU_0x24, GBEMU_0x74, GBEMU_0x12, GBEMU_0xFC, GBEMU_0x00, GBEMU_0x9F, GBEMU_0xB4, GBEMU_0xB7, GBEMU_0x06, GBEMU_0xD5, GBEMU_0xD0, GBEMU_0x7A, GBEMU_0x00, GBEMU_0x9E, GBEMU_0x04, GBEMU_0x5F, GBEMU_0x41, GBEMU_0x2F, GBEMU_0x1D, GBEMU_0x77, GBEMU_0x36, GBEMU_0x75, GBEMU_0x81, GBEMU_0xAA, GBEMU_0x70, GBEMU_0x3A, GBEMU_0x98, GBEMU_0xD1, GBEMU_0x71, GBEMU_0x02, GBEMU_0x4D, GBEMU_0x01, GBEMU_0xC1, GBEMU_0xFF, GBEMU_0x0D, GBEMU_0x00, GBEMU_0xD3, GBEMU_0x05, GBEMU_0xF9, GBEMU_0x00, GBEMU_0x0B, GBEMU_0x00
         };
 
         // other perpty
         public static int channel1FrequencyTracker = GBEMU_0x2000;
         public static int channel1DutyTracker = 0;
         public static boolean[] channel1CachedDuty = {};
         public static int channel1totalLength = 0;
         public static int channel1envelopeVolume = 0;
         public static boolean channel1envelopeType = false;
         public static int channel1envelopeSweeps = 0;
         public static int channel1envelopeSweepsLast = 0;
         public static boolean channel1consecutive = true;
         public static int channel1frequency = GBEMU_1985;
         public static boolean channel1SweepFault = true;
         public static int channel1ShadowFrequency = GBEMU_1985;
         public static int channel1timeSweep = 1;
         public int channel1lastTimeSweep = 0;
         public int channel1numSweep = 0;
         public int channel1frequencySweepDivider = 0;
         public boolean channel1decreaseSweep = false;
         public int channel2FrequencyTracker = GBEMU_0x2000;
         public int channel2DutyTracker = 0;
         public boolean[] channel2CachedDuty = {};
         public int channel2totalLength = 0;
         public int channel2envelopeVolume = 0;
         public boolean channel2envelopeType = false;
         public int channel2envelopeSweeps = 0;
         public int channel2envelopeSweepsLast = 0;
         public boolean channel2consecutive = true;
         public int channel2frequency = 0;
         public boolean channel3canPlay = false;
         public int channel3totalLength = 0;
         public int channel3patternType = GBEMU_4;
         public int channel3frequency = 0;
         public boolean channel3consecutive = true;
         public int channel3Counter = GBEMU_0x418;
         public int channel4FrequencyPeriod = GBEMU_8;
         public int channel4totalLength = 0;
         public int channel4envelopeVolume = 0;
         public int channel4currentVolume = 0;
         public boolean channel4envelopeType = false;
         public int channel4envelopeSweeps = 0;
         public int channel4envelopeSweepsLast = 0;
         public boolean channel4consecutive = true;
         public int channel4BitRange = GBEMU_0x7FFF;
         public int channel4VolumeShifter = GBEMU_15;
         public int channel1FrequencyCounter = GBEMU_0x200;
         public int channel2FrequencyCounter = GBEMU_0x200;
         public int channel3FrequencyPeriod = GBEMU_0x800;
         public int channel3lastSampleLookup = 0;
         public int channel4lastSampleLookup = 0;
         public int sequencerClocks = GBEMU_0x2000;
         public int sequencePosition = 0;
         public int channel4Counter = GBEMU_8;
         public int cachedChannel3Sample = 0;
         public int cachedChannel4Sample = 0;
         public boolean channel1Enabled = false;
         public boolean channel2Enabled = false;
         public boolean channel3Enabled = false;
         public boolean channel4Enabled = false;
         public boolean channel1canPlay = false;
         public boolean channel2canPlay = false;
         public boolean channel4canPlay = false;
         public int romBankEdge = 0;
         public boolean cBATT = false;
         public static ArrayList<Integer> oamAddressCache = new ArrayList<>();
         public static ArrayList<Integer> sortBuffer = new ArrayList<>();
         public Resize resizer = null;
         public int instructions = 0;
         public int totalInstructions = 0;
         public GameBoyContext drawContextOnscreen = new GameBoyContext();
         public GameBoyContext drawContextOffscreen = new GameBoyContext();
         public GameBoyCanvas canvasOffscreen = new GameBoyCanvas();
         public GbemuPartOpenMBC openMBC = null;
         public GbemuPartOpenRTC openRTC = null;
         public int numRomBanks = 0;
         public int[] tickTable = {
                 // Number of machine cycles for each instruction:
                 GBEMU_4, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_20, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 0
                 GBEMU_4, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 1
                 GBEMU_8, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 2
                 GBEMU_8, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_12, GBEMU_12, GBEMU_4, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 3
 
                 GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 4
                 GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 5
                 GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 6
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 7
 
                 GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 8
                 GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // 9
                 GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // A
                 GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_4, // B
 
                 GBEMU_8, GBEMU_12, GBEMU_12, GBEMU_16, GBEMU_12, GBEMU_16, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_16, GBEMU_12, 0, GBEMU_12, GBEMU_24, GBEMU_8, GBEMU_16, // C
                 GBEMU_8, GBEMU_12, GBEMU_12, GBEMU_4, GBEMU_12, GBEMU_16, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_16, GBEMU_12, GBEMU_4, GBEMU_12, GBEMU_4, GBEMU_8, GBEMU_16, // D
                 GBEMU_12, GBEMU_12, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_16, GBEMU_8, GBEMU_16, GBEMU_16, GBEMU_4, GBEMU_16, GBEMU_4, GBEMU_4, GBEMU_4, GBEMU_8, GBEMU_16, // E
                 GBEMU_12, GBEMU_12, GBEMU_8, GBEMU_4, GBEMU_4, GBEMU_16, GBEMU_8, GBEMU_16, GBEMU_12, GBEMU_8, GBEMU_16, GBEMU_4, 0, GBEMU_4, GBEMU_8, GBEMU_16 // F
         };
         public int[] secondaryTickTable = {
                 // Number of machine cycles for each 0xCBXX instruction:
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // 0
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // 1
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // 2
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // 3
 
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_8, // 4
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_8, // 5
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_8, // 6
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_12, GBEMU_8, // 7
 
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // 8
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // 9
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // A
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // B
 
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // C
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // D
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, // E
                 GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_8, GBEMU_16, GBEMU_8 // F
         };
 
         public GbemuPartCodeFun[] opCode = new GbemuPartCodeFun[]{
                 // NOP
                 // #0x00:
                 (parentObj) -> {
                     // Do Nothing...
                 },
                 // LD BC, nn
                 // #0x01:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.registerB = parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF);
                     parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // LD (BC), A
                 // #0x02:
                 (parentObj) -> {
                     parentObj.memoryWrite((parentObj.registerB << GBEMU_8) | parentObj.registerC, parentObj.registerA);
                 },
                 // INC BC
                 // #0x03:
                 (parentObj) -> {
                     int tempVar = ((parentObj.registerB << GBEMU_8) | parentObj.registerC) + 1;
                     parentObj.registerB = (tempVar >> GBEMU_8) & GBEMU_0xFF;
                     parentObj.registerC = tempVar & GBEMU_0xFF;
                 },
                 // INC B
                 // #0x04:
                 (parentObj) -> {
                     parentObj.registerB = (parentObj.registerB + 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerB == 0;
                     parentObj.fHalfCarry = (parentObj.registerB & GBEMU_0xF) == 0;
                     parentObj.fSubtract = false;
                 },
                 // DEC B
                 // #0x05:
                 (parentObj) -> {
                     parentObj.registerB = (parentObj.registerB - 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerB == 0;
                     parentObj.fHalfCarry = (parentObj.registerB & GBEMU_0xF) == GBEMU_0xF;
                     parentObj.fSubtract = true;
                 },
                 // LD B, n
                 // #0x06:
                 (parentObj) -> {
                     parentObj.registerB = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // RLCA
                 // #0x07:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerA > GBEMU_0x7F;
                     parentObj.registerA = ((parentObj.registerA << 1) & GBEMU_0xFF) | (parentObj.registerA >> GBEMU_7);
                     parentObj.fZero = false;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                 },
                 // LD (nn), SP
                 // #0x08:
                 (parentObj) -> {
                     int tempVar = (parentObj
                             .memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                             parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     parentObj.memoryWrite(tempVar, parentObj.stackPointer & GBEMU_0xFF);
                     parentObj.memoryWrite((tempVar + 1) & GBEMU_0xFFFF, parentObj.stackPointer >> GBEMU_8);
                 },
                 // ADD HL, BC
                 // #0x09:
                 (parentObj) -> {
                     int dirtySum = parentObj.registersHL + ((parentObj.registerB << GBEMU_8) | parentObj.registerC);
                     parentObj.fHalfCarry = (parentObj.registersHL & GBEMU_0xFFF) > (dirtySum & GBEMU_0xFFF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFFFF;
                     parentObj.registersHL = dirtySum & GBEMU_0xFFFF;
                     parentObj.fSubtract = false;
                 },
                 // LD A, (BC)
                 // #0x0A:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryRead((parentObj.registerB << GBEMU_8) | parentObj.registerC);
                 },
                 // DEC BC
                 // #0x0B:
                 (parentObj) -> {
                     int tempVar = (((parentObj.registerB << GBEMU_8) | parentObj.registerC) - 1) & GBEMU_0xFFFF;
                     parentObj.registerB = tempVar >> GBEMU_8;
                     parentObj.registerC = tempVar & GBEMU_0xFF;
                 },
                 // INC C
                 // #0x0C:
                 (parentObj) -> {
                     parentObj.registerC = (parentObj.registerC + 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerC == 0;
                     parentObj.fHalfCarry = (parentObj.registerC & GBEMU_0xF) == 0;
                     parentObj.fSubtract = false;
                 },
                 // DEC C
                 // #0x0D:
                 (parentObj) -> {
                     parentObj.registerC = (parentObj.registerC - 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerC == 0;
                     parentObj.fHalfCarry = (parentObj.registerC & GBEMU_0xF) == GBEMU_0xF;
                     parentObj.fSubtract = true;
                 },
                 // LD C, n
                 // #0x0E:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // RRCA
                 // #0x0F:
                 (parentObj) -> {
                     parentObj.registerA = (parentObj.registerA >> 1) | ((parentObj.registerA & 1) << GBEMU_7);
                     parentObj.fCarry = parentObj.registerA > GBEMU_0x7F;
                     parentObj.fZero = false;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                 },
                 // STOP
                 // #0x10:
                 (parentObj) -> {
                     if (parentObj.cGBC) {
                         if ((parentObj.memory.get(GBEMU_0xFF4D) & GBEMU_0x01) == GBEMU_0x01) {
                             // Speed change requested.
                             Integer gbemu0xFF4D = parentObj.memory.get(GBEMU_0xFF4D);
                             if (parentObj.memory.get(GBEMU_0xFF4D) > GBEMU_0x7F) {
                                 // Go back to single speed mode.
                                 cout("Going into single clock speed mode.", 0);
                                 parentObj.doubleSpeedShifter = 0;
                                 gbemu0xFF4D &= GBEMU_0x7F;
                                 parentObj.memory.set(GBEMU_0xFF4D, gbemu0xFF4D); // Clear the double speed mode flag.
                             } else {
                                 // Go to double speed mode.
                                 cout("Going into double clock speed mode.", 0);
                                 parentObj.doubleSpeedShifter = 1;
                                 gbemu0xFF4D |= GBEMU_0x80;
                                 parentObj.memory.set(GBEMU_0xFF4D, gbemu0xFF4D); // Set the double speed mode flag.
                             }
                             gbemu0xFF4D &= GBEMU_0xFE;
                             parentObj.memory.set(GBEMU_0xFF4D, gbemu0xFF4D); // Reset the request bit.
                         } else {
                             parentObj.handleSTOP(); // Handle Stop
                         }
                     } else {
                         parentObj.handleSTOP();
                     }
                 },
                 // LD DE, nn
                 // #0x11:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.registerD = parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF);
                     parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // LD (DE), A
                 // #0x12:
                 (parentObj) -> {
                     parentObj.memoryWrite((parentObj.registerD << GBEMU_8) | parentObj.registerE, parentObj.registerA);
                 },
                 // INC DE
                 // #0x13:
                 (parentObj) -> {
                     int tempVar = ((parentObj.registerD << GBEMU_8) | parentObj.registerE) + 1;
                     parentObj.registerD = (tempVar >> GBEMU_8) & GBEMU_0xFF;
                     parentObj.registerE = tempVar & GBEMU_0xFF;
                 },
                 // INC D
                 // #0x14:
                 (parentObj) -> {
                     parentObj.registerD = (parentObj.registerD + 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerD == 0;
                     parentObj.fHalfCarry = (parentObj.registerD & GBEMU_0xF) == 0;
                     parentObj.fSubtract = false;
                 },
                 // DEC D
                 // #0x15:
                 (parentObj) -> {
                     parentObj.registerD = (parentObj.registerD - 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerD == 0;
                     parentObj.fHalfCarry = (parentObj.registerD & GBEMU_0xF) == GBEMU_0xF;
                     parentObj.fSubtract = true;
                 },
                 // LD D, n
                 // #0x16:
                 (parentObj) -> {
                     parentObj.registerD = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // RLA
                 // #0x17:
                 (parentObj) -> {
                     int carry_flag = parentObj.fCarry ? 1 : 0;
                     parentObj.fCarry = parentObj.registerA > GBEMU_0x7F;
                     parentObj.registerA = ((parentObj.registerA << 1) & GBEMU_0xFF) | carry_flag;
                     parentObj.fZero = false;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                 },
                 // JR n
                 // #0x18:
                 (parentObj) -> {
                     parentObj.programCounter =
                             (parentObj.programCounter + ((parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) << GBEMU_24) >> GBEMU_24) + 1) &
                                     GBEMU_0xFFFF;
                 },
                 // ADD HL, DE
                 // #0x19:
                 (parentObj) -> {
                     int dirtySum = parentObj.registersHL + ((parentObj.registerD << GBEMU_8) | parentObj.registerE);
                     parentObj.fHalfCarry = (parentObj.registersHL & GBEMU_0xFFF) > (dirtySum & GBEMU_0xFFF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFFFF;
                     parentObj.registersHL = dirtySum & GBEMU_0xFFFF;
                     parentObj.fSubtract = false;
                 },
                 // LD A, (DE)
                 // #0x1A:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryRead((parentObj.registerD << GBEMU_8) | parentObj.registerE);
                 },
                 // DEC DE
                 // #0x1B:
                 (parentObj) -> {
                     int tempVar = (((parentObj.registerD << GBEMU_8) | parentObj.registerE) - 1) & GBEMU_0xFFFF;
                     parentObj.registerD = tempVar >> GBEMU_8;
                     parentObj.registerE = tempVar & GBEMU_0xFF;
                 },
                 // INC E
                 // #0x1C:
                 (parentObj) -> {
                     parentObj.registerE = (parentObj.registerE + 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerE == 0;
                     parentObj.fHalfCarry = (parentObj.registerE & GBEMU_0xF) == 0;
                     parentObj.fSubtract = false;
                 },
                 // DEC E
                 // #0x1D:
                 (parentObj) -> {
                     parentObj.registerE = (parentObj.registerE - 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerE == 0;
                     parentObj.fHalfCarry = (parentObj.registerE & GBEMU_0xF) == GBEMU_0xF;
                     parentObj.fSubtract = true;
                 },
                 // LD E, n
                 // #0x1E:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // RRA
                 // #0x1F:
                 (parentObj) -> {
                     int carry_flag = parentObj.fCarry ? GBEMU_0x80 : 0;
                     parentObj.fCarry = (parentObj.registerA & 1) == 1;
                     parentObj.registerA = (parentObj.registerA >> 1) | carry_flag;
                     parentObj.fZero = false;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                 },
                 // JR NZ, n
                 // #0x20:
                 (parentObj) -> {
                     if (!parentObj.fZero) {
                         parentObj.programCounter =
                                 (parentObj.programCounter + ((parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) << GBEMU_24) >> GBEMU_24) + 1) &
                                         GBEMU_0xFFFF;
                         parentObj.cpuTicks += GBEMU_4;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     }
                 },
                 // LD HL, nn
                 // #0x21:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj
                             .memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                             parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // LDI (HL), A
                 // #0x22:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registerA);
                     parentObj.registersHL = (parentObj.registersHL + 1) & GBEMU_0xFFFF;
                 },
                 // INC HL
                 // #0x23:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL + 1) & GBEMU_0xFFFF;
                 },
                 // INC H
                 // #0x24:
                 (parentObj) -> {
                     int h = ((parentObj.registersHL >> GBEMU_8) + 1) & GBEMU_0xFF;
                     parentObj.fZero = h == 0;
                     parentObj.fHalfCarry = (h & GBEMU_0xF) == 0;
                     parentObj.fSubtract = false;
                     parentObj.registersHL = (h << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                 },
                 // DEC H
                 // #0x25:
                 (parentObj) -> {
                     int h = ((parentObj.registersHL >> GBEMU_8) - 1) & GBEMU_0xFF;
                     parentObj.fZero = h == 0;
                     parentObj.fHalfCarry = (h & GBEMU_0xF) == GBEMU_0xF;
                     parentObj.fSubtract = true;
                     parentObj.registersHL = (h << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                 },
                 // LD H, n
                 // #0x26:
                 (parentObj) -> {
                     parentObj.registersHL =
                             (parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // DAA
                 // #0x27:
                 (parentObj) -> {
                     if (!parentObj.fSubtract) {
                         if (parentObj.fCarry || parentObj.registerA > GBEMU_0x99) {
                             parentObj.registerA = (parentObj.registerA + GBEMU_0x60) & GBEMU_0xFF;
                             parentObj.fCarry = true;
                         }
                         if (parentObj.fHalfCarry || (parentObj.registerA & GBEMU_0xF) > GBEMU_0x9) {
                             parentObj.registerA = (parentObj.registerA + GBEMU_0x06) & GBEMU_0xFF;
                             parentObj.fHalfCarry = false;
                         }
                     } else if (parentObj.fCarry && parentObj.fHalfCarry) {
                         parentObj.registerA = (parentObj.registerA + GBEMU_0x9A) & GBEMU_0xFF;
                         parentObj.fHalfCarry = false;
                     } else if (parentObj.fCarry) {
                         parentObj.registerA = (parentObj.registerA + GBEMU_0xA0) & GBEMU_0xFF;
                     } else if (parentObj.fHalfCarry) {
                         parentObj.registerA = (parentObj.registerA + GBEMU_0xFA) & GBEMU_0xFF;
                         parentObj.fHalfCarry = false;
                     }
                     parentObj.fZero = parentObj.registerA == 0;
                 },
                 // JR Z, n
                 // #0x28:
                 (parentObj) -> {
                     if (parentObj.fZero) {
                         parentObj.programCounter =
                                 (parentObj.programCounter + ((parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) << GBEMU_24) >> GBEMU_24) + 1) &
                                         GBEMU_0xFFFF;
                         parentObj.cpuTicks += GBEMU_4;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     }
                 },
                 // ADD HL, HL
                 // #0x29:
                 (parentObj) -> {
                     parentObj.fHalfCarry = (parentObj.registersHL & GBEMU_0xFFF) > GBEMU_0x7FF;
                     parentObj.fCarry = parentObj.registersHL > GBEMU_0x7FFF;
                     parentObj.registersHL = (parentObj.registersHL << 1) & GBEMU_0xFFFF;
                     parentObj.fSubtract = false;
                 },
                 // LDI A, (HL)
                 // #0x2A:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.registersHL = (parentObj.registersHL + 1) & GBEMU_0xFFFF;
                 },
                 // DEC HL
                 // #0x2B:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL - 1) & GBEMU_0xFFFF;
                 },
                 // INC L
                 // #0x2C:
                 (parentObj) -> {
                     int L = (parentObj.registersHL + 1) & GBEMU_0xFF;
                     parentObj.fZero = L == 0;
                     parentObj.fHalfCarry = (L & GBEMU_0xF) == 0;
                     parentObj.fSubtract = false;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | L;
                 },
                 // DEC L
                 // #0x2D:
                 (parentObj) -> {
                     int L = (parentObj.registersHL - 1) & GBEMU_0xFF;
                     parentObj.fZero = L == 0;
                     parentObj.fHalfCarry = (L & GBEMU_0xF) == GBEMU_0xF;
                     parentObj.fSubtract = true;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | L;
                 },
                 // LD L, n
                 // #0x2E:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // CPL
                 // #0x2F:
                 (parentObj) -> {
                     parentObj.registerA ^= GBEMU_0xFF;
                     parentObj.fSubtract = true;
                     parentObj.fHalfCarry = true;
                 },
                 // JR NC, n
                 // #0x30:
                 (parentObj) -> {
                     if (!parentObj.fCarry) {
                         parentObj.programCounter =
                                 (parentObj.programCounter + ((parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) << GBEMU_24) >> GBEMU_24) + 1) &
                                         GBEMU_0xFFFF;
                         parentObj.cpuTicks += GBEMU_4;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     }
                 },
                 // LD SP, nn
                 // #0x31:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj
                             .memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                             parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // LDD (HL), A
                 // #0x32:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registerA);
                     parentObj.registersHL = (parentObj.registersHL - 1) & GBEMU_0xFFFF;
                 },
                 // INC SP
                 // #0x33:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer + 1) & GBEMU_0xFFFF;
                 },
                 // INC (HL)
                 // #0x34:
                 (parentObj) -> {
                     int tempVar = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) + 1) & GBEMU_0xFF;
                     parentObj.fZero = tempVar == 0;
                     parentObj.fHalfCarry = (tempVar & GBEMU_0xF) == 0;
                     parentObj.fSubtract = false;
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                 },
                 // DEC (HL)
                 // #0x35:
                 (parentObj) -> {
                     int tempVar = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) - 1) & GBEMU_0xFF;
                     parentObj.fZero = tempVar == 0;
                     parentObj.fHalfCarry = (tempVar & GBEMU_0xF) == GBEMU_0xF;
                     parentObj.fSubtract = true;
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                 },
                 // LD (HL), n
                 // #0x36:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter)
                     );
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // SCF
                 // #0x37:
                 (parentObj) -> {
                     parentObj.fCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                 },
                 // JR C, n
                 // #0x38:
                 (parentObj) -> {
                     if (parentObj.fCarry) {
                         parentObj.programCounter =
                                 (parentObj.programCounter + ((parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) << GBEMU_24) >> GBEMU_24) + 1) &
                                         GBEMU_0xFFFF;
                         parentObj.cpuTicks += GBEMU_4;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     }
                 },
                 // ADD HL, SP
                 // #0x39:
                 (parentObj) -> {
                     int dirtySum = parentObj.registersHL + parentObj.stackPointer;
                     parentObj.fHalfCarry = (parentObj.registersHL & GBEMU_0xFFF) > (dirtySum & GBEMU_0xFFF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFFFF;
                     parentObj.registersHL = dirtySum & GBEMU_0xFFFF;
                     parentObj.fSubtract = false;
                 },
                 // LDD A, (HL)
                 // #0x3A:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.registersHL = (parentObj.registersHL - 1) & GBEMU_0xFFFF;
                 },
                 // DEC SP
                 // #0x3B:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                 },
                 // INC A
                 // #0x3C:
                 (parentObj) -> {
                     parentObj.registerA = (parentObj.registerA + 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) == 0;
                     parentObj.fSubtract = false;
                 },
                 // DEC A
                 // #0x3D:
                 (parentObj) -> {
                     parentObj.registerA = (parentObj.registerA - 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) == GBEMU_0xF;
                     parentObj.fSubtract = true;
                 },
                 // LD A, n
                 // #0x3E:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // CCF
                 // #0x3F:
                 (parentObj) -> {
                     parentObj.fCarry = !parentObj.fCarry;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                 },
                 // LD B, B
                 // #0x40:
                 (parentObj) -> {
                     // Do nothing...
                 },
                 // LD B, C
                 // #0x41:
                 (parentObj) -> {
                     parentObj.registerB = parentObj.registerC;
                 },
                 // LD B, D
                 // #0x42:
                 (parentObj) -> {
                     parentObj.registerB = parentObj.registerD;
                 },
                 // LD B, E
                 // #0x43:
                 (parentObj) -> {
                     parentObj.registerB = parentObj.registerE;
                 },
                 // LD B, H
                 // #0x44:
                 (parentObj) -> {
                     parentObj.registerB = parentObj.registersHL >> GBEMU_8;
                 },
                 // LD B, L
                 // #0x45:
                 (parentObj) -> {
                     parentObj.registerB = parentObj.registersHL & GBEMU_0xFF;
                 },
                 // LD B, (HL)
                 // #0x46:
                 (parentObj) -> {
                     parentObj.registerB = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                 },
                 // LD B, A
                 // #0x47:
                 (parentObj) -> {
                     parentObj.registerB = parentObj.registerA;
                 },
                 // LD C, B
                 // #0x48:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.registerB;
                 },
                 // LD C, C
                 // #0x49:
                 (parentObj) -> {
                     // Do nothing...
                 },
                 // LD C, D
                 // #0x4A:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.registerD;
                 },
                 // LD C, E
                 // #0x4B:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.registerE;
                 },
                 // LD C, H
                 // #0x4C:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.registersHL >> GBEMU_8;
                 },
                 // LD C, L
                 // #0x4D:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.registersHL & GBEMU_0xFF;
                 },
                 // LD C, (HL)
                 // #0x4E:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                 },
                 // LD C, A
                 // #0x4F:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.registerA;
                 },
                 // LD D, B
                 // #0x50:
                 (parentObj) -> {
                     parentObj.registerD = parentObj.registerB;
                 },
                 // LD D, C
                 // #0x51:
                 (parentObj) -> {
                     parentObj.registerD = parentObj.registerC;
                 },
                 // LD D, D
                 // #0x52:
                 (parentObj) -> {
                     // Do nothing...
                 },
                 // LD D, E
                 // #0x53:
                 (parentObj) -> {
                     parentObj.registerD = parentObj.registerE;
                 },
                 // LD D, H
                 // #0x54:
                 (parentObj) -> {
                     parentObj.registerD = parentObj.registersHL >> GBEMU_8;
                 },
                 // LD D, L
                 // #0x55:
                 (parentObj) -> {
                     parentObj.registerD = parentObj.registersHL & GBEMU_0xFF;
                 },
                 // LD D, (HL)
                 // #0x56:
                 (parentObj) -> {
                     parentObj.registerD = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                 },
                 // LD D, A
                 // #0x57:
                 (parentObj) -> {
                     parentObj.registerD = parentObj.registerA;
                 },
                 // LD E, B
                 // #0x58:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.registerB;
                 },
                 // LD E, C
                 // #0x59:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.registerC;
                 },
                 // LD E, D
                 // #0x5A:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.registerD;
                 },
                 // LD E, E
                 // #0x5B:
                 (parentObj) -> {
                     // Do nothing...
                 },
                 // LD E, H
                 // #0x5C:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.registersHL >> GBEMU_8;
                 },
                 // LD E, L
                 // #0x5D:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.registersHL & GBEMU_0xFF;
                 },
                 // LD E, (HL)
                 // #0x5E:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                 },
                 // LD E, A
                 // #0x5F:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.registerA;
                 },
                 // LD H, B
                 // #0x60:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registerB << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                 },
                 // LD H, C
                 // #0x61:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registerC << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                 },
                 // LD H, D
                 // #0x62:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registerD << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                 },
                 // LD H, E
                 // #0x63:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registerE << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                 },
                 // LD H, H
                 // #0x64:
                 (parentObj) -> {
                     // Do nothing...
                 },
                 // LD H, L
                 // #0x65:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF) * GBEMU_0x101;
                 },
                 // LD H, (HL)
                 // #0x66:
                 (parentObj) -> {
                     parentObj.registersHL =
                             (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                 },
                 // LD H, A
                 // #0x67:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registerA << GBEMU_8) | (parentObj.registersHL & GBEMU_0xFF);
                 },
                 // LD L, B
                 // #0x68:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | parentObj.registerB;
                 },
                 // LD L, C
                 // #0x69:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | parentObj.registerC;
                 },
                 // LD L, D
                 // #0x6A:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | parentObj.registerD;
                 },
                 // LD L, E
                 // #0x6B:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | parentObj.registerE;
                 },
                 // LD L, H
                 // #0x6C:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | (parentObj.registersHL >> GBEMU_8);
                 },
                 // LD L, L
                 // #0x6D:
                 (parentObj) -> {
                     // Do nothing...
                 },
                 // LD L, (HL)
                 // #0x6E:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                 },
                 // LD L, A
                 // #0x6F:
                 (parentObj) -> {
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | parentObj.registerA;
                 },
                 // LD (HL), B
                 // #0x70:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registerB);
                 },
                 // LD (HL), C
                 // #0x71:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registerC);
                 },
                 // LD (HL), D
                 // #0x72:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registerD);
                 },
                 // LD (HL), E
                 // #0x73:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registerE);
                 },
                 // LD (HL), H
                 // #0x74:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registersHL >> GBEMU_8);
                 },
                 // LD (HL), L
                 // #0x75:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registersHL & GBEMU_0xFF);
                 },
                 // HALT
                 // #0x76:
                 (parentObj) -> {
                     // See if there's already an IRQ match:
                     if ((parentObj.interruptsEnabled & parentObj.interruptsRequested & GBEMU_0x1F) > 0) {
                         if (!parentObj.cGBC && !parentObj.usedBootrom) {
                             // HALT bug in the DMG CPU model (Program Counter fails to increment for one instruction after HALT):
                             parentObj.skipPCIncrement = true;
                         } else {
                             // CGB gets around the HALT PC bug by doubling the hidden NOP.
                             parentObj.cpuTicks += GBEMU_4;
                         }
                     } else {
                         // CPU is stalled until the next IRQ match:
                         parentObj.calculateHALTPeriod();
                     }
                 },
                 // LD (HL), A
                 // #0x77:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, parentObj.registerA);
                 },
                 // LD A, B
                 // #0x78:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.registerB;
                 },
                 // LD A, C
                 // #0x79:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.registerC;
                 },
                 // LD A, D
                 // #0x7A:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.registerD;
                 },
                 // LD A, E
                 // #0x7B:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.registerE;
                 },
                 // LD A, H
                 // #0x7C:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.registersHL >> GBEMU_8;
                 },
                 // LD A, L
                 // #0x7D:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.registersHL & GBEMU_0xFF;
                 },
                 // LD, A, (HL)
                 // #0x7E:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                 },
                 // LD A, A
                 // #0x7F:
                 (parentObj) -> {
                     // Do Nothing...
                 },
                 // ADD A, B
                 // #0x80:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.registerB;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) < (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADD A, C
                 // #0x81:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.registerC;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) < (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADD A, D
                 // #0x82:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.registerD;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) < (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADD A, E
                 // #0x83:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.registerE;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) < (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADD A, H
                 // #0x84:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + (parentObj.registersHL >> GBEMU_8);
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) < (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADD A, L
                 // #0x85:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) < (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADD A, (HL)
                 // #0x86:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) < (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADD A, A
                 // #0x87:
                 (parentObj) -> {
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0x8) == GBEMU_0x8;
                     parentObj.fCarry = parentObj.registerA > GBEMU_0x7F;
                     parentObj.registerA = (parentObj.registerA << 1) & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADC A, B
                 // #0x88:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.registerB + (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) + (parentObj.registerB & GBEMU_0xF) + (parentObj.fCarry ? 1 : 0) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADC A, C
                 // #0x89:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.registerC + (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) + (parentObj.registerC & GBEMU_0xF) + (parentObj.fCarry ? 1 : 0) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADC A, D
                 // #0x8A:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.registerD + (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) + (parentObj.registerD & GBEMU_0xF) + (parentObj.fCarry ? 1 : 0) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADC A, E
                 // #0x8B:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.registerE + (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) + (parentObj.registerE & GBEMU_0xF) + (parentObj.fCarry ? 1 : 0) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADC A, H
                 // #0x8C:
                 (parentObj) -> {
                     int tempValue = parentObj.registersHL >> GBEMU_8;
                     int dirtySum = parentObj.registerA + tempValue + (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) + (tempValue & GBEMU_0xF) + (parentObj.fCarry ? 1 : 0) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADC A, L
                 // #0x8D:
                 (parentObj) -> {
                     int tempValue = parentObj.registersHL & GBEMU_0xFF;
                     int dirtySum = parentObj.registerA + tempValue + (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) + (tempValue & GBEMU_0xF) + (parentObj.fCarry ? 1 : 0) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADC A, (HL)
                 // #0x8E:
                 (parentObj) -> {
                     int tempValue = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     int dirtySum = parentObj.registerA + tempValue + (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) + (tempValue & GBEMU_0xF) + (parentObj.fCarry ? 1 : 0) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // ADC A, A
                 // #0x8F:
                 (parentObj) -> {
                     // shift left register A one bit for some ops here as an optimization:
                     int dirtySum = (parentObj.registerA << 1) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (((parentObj.registerA << 1) & GBEMU_0x1E) | (parentObj.fCarry ? 1 : 0)) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // SUB A, B
                 // #0x90:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerB;
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) < (dirtySum & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // SUB A, C
                 // #0x91:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerC;
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) < (dirtySum & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // SUB A, D
                 // #0x92:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerD;
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) < (dirtySum & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // SUB A, E
                 // #0x93:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerE;
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) < (dirtySum & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // SUB A, H
                 // #0x94:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - (parentObj.registersHL >> GBEMU_8);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) < (dirtySum & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // SUB A, L
                 // #0x95:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) < (dirtySum & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // SUB A, (HL)
                 // #0x96:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) < (dirtySum & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // SUB A, A
                 // #0x97:
                 (parentObj) -> {
                     // number - same number == 0
                     parentObj.registerA = 0;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                     parentObj.fZero = true;
                     parentObj.fSubtract = true;
                 },
                 // SBC A, B
                 // #0x98:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerB - (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) - (parentObj.registerB & GBEMU_0xF) - (parentObj.fCarry ? 1 : 0) < 0;
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = true;
                 },
                 // SBC A, C
                 // #0x99:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerC - (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) - (parentObj.registerC & GBEMU_0xF) - (parentObj.fCarry ? 1 : 0) < 0;
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = true;
                 },
                 // SBC A, D
                 // #0x9A:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerD - (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) - (parentObj.registerD & GBEMU_0xF) - (parentObj.fCarry ? 1 : 0) < 0;
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = true;
                 },
                 // SBC A, E
                 // #0x9B:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerE - (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) - (parentObj.registerE & GBEMU_0xF) - (parentObj.fCarry ? 1 : 0) < 0;
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = true;
                 },
                 // SBC A, H
                 // #0x9C:
                 (parentObj) -> {
                     int tempVar = parentObj.registersHL >> GBEMU_8;
                     int dirtySum = parentObj.registerA - tempVar - (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) - (tempVar & GBEMU_0xF) - (parentObj.fCarry ? 1 : 0) < 0;
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = true;
                 },
                 // SBC A, L
                 // #0x9D:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - (parentObj.registersHL & GBEMU_0xFF) - (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) - (parentObj.registersHL & GBEMU_0xF) - (parentObj.fCarry ? 1 : 0) < 0;
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = true;
                 },
                 // SBC A, (HL)
                 // #0x9E:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     int dirtySum = parentObj.registerA - tempVar - (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) - (tempVar & GBEMU_0xF) - (parentObj.fCarry ? 1 : 0) < 0;
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = true;
                 },
                 // SBC A, A
                 // #0x9F:
                 (parentObj) -> {
                     // Optimized SBC A:
                     if (parentObj.fCarry) {
                         parentObj.fZero = false;
                         parentObj.fSubtract = true;
                         parentObj.fHalfCarry = true;
                         parentObj.fCarry = true;
                         parentObj.registerA = GBEMU_0xFF;
                     } else {
                         parentObj.fHalfCarry = false;
                         parentObj.fCarry = false;
                         parentObj.fSubtract = true;
                         parentObj.fZero = true;
                         parentObj.registerA = 0;
                     }
                 },
                 // AND B
                 // #0xA0:
                 (parentObj) -> {
                     parentObj.registerA &= parentObj.registerB;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // AND C
                 // #0xA1:
                 (parentObj) -> {
                     parentObj.registerA &= parentObj.registerC;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // AND D
                 // #0xA2:
                 (parentObj) -> {
                     parentObj.registerA &= parentObj.registerD;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // AND E
                 // #0xA3:
                 (parentObj) -> {
                     parentObj.registerA &= parentObj.registerE;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // AND H
                 // #0xA4:
                 (parentObj) -> {
                     parentObj.registerA &= parentObj.registersHL >> GBEMU_8;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // AND L
                 // #0xA5:
                 (parentObj) -> {
                     parentObj.registerA &= parentObj.registersHL;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // AND (HL)
                 // #0xA6:
                 (parentObj) -> {
                     parentObj.registerA &= parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // AND A
                 // #0xA7:
                 (parentObj) -> {
                     // number & same number = same number
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // XOR B
                 // #0xA8:
                 (parentObj) -> {
                     parentObj.registerA ^= parentObj.registerB;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // XOR C
                 // #0xA9:
                 (parentObj) -> {
                     parentObj.registerA ^= parentObj.registerC;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // XOR D
                 // #0xAA:
                 (parentObj) -> {
                     parentObj.registerA ^= parentObj.registerD;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // XOR E
                 // #0xAB:
                 (parentObj) -> {
                     parentObj.registerA ^= parentObj.registerE;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // XOR H
                 // #0xAC:
                 (parentObj) -> {
                     parentObj.registerA ^= parentObj.registersHL >> GBEMU_8;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // XOR L
                 // #0xAD:
                 (parentObj) -> {
                     parentObj.registerA ^= parentObj.registersHL & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // XOR (HL)
                 // #0xAE:
                 (parentObj) -> {
                     parentObj.registerA ^= parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // XOR A
                 // #0xAF:
                 (parentObj) -> {
                     // number ^ same number == 0
                     parentObj.registerA = 0;
                     parentObj.fZero = true;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // OR B
                 // #0xB0:
                 (parentObj) -> {
                     parentObj.registerA |= parentObj.registerB;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // OR C
                 // #0xB1:
                 (parentObj) -> {
                     parentObj.registerA |= parentObj.registerC;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // OR D
                 // #0xB2:
                 (parentObj) -> {
                     parentObj.registerA |= parentObj.registerD;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // OR E
                 // #0xB3:
                 (parentObj) -> {
                     parentObj.registerA |= parentObj.registerE;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // OR H
                 // #0xB4:
                 (parentObj) -> {
                     parentObj.registerA |= parentObj.registersHL >> GBEMU_8;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // OR L
                 // #0xB5:
                 (parentObj) -> {
                     parentObj.registerA |= parentObj.registersHL & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // OR (HL)
                 // #0xB6:
                 (parentObj) -> {
                     parentObj.registerA |= parentObj.memoryReader.get(parentObj.registersHL).call(parentObj,parentObj.registersHL);
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // OR A
                 // #0xB7:
                 (parentObj) -> {
                     // number | same number == same number
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // CP B
                 // #0xB8:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerB;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) > (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // CP C
                 // #0xB9:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerC;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) > (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // CP D
                 // #0xBA:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerD;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) > (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // CP E
                 // #0xBB:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.registerE;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) > (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // CP H
                 // #0xBC:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - (parentObj.registersHL >> GBEMU_8);
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) > (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // CP L
                 // #0xBD:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) > (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // CP (HL)
                 // #0xBE:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) > (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // CP A
                 // #0xBF:
                 (parentObj) -> {
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                     parentObj.fZero = true;
                     parentObj.fSubtract = true;
                 },
                 // RET !FZ
                 // #0xC0:
                 (parentObj) -> {
                     if (!parentObj.fZero) {
                         parentObj.programCounter = (parentObj
                                 .memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                 parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                         parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                         parentObj.cpuTicks += GBEMU_12;
                     }
                 },
                 // POP BC
                 // #0xC1:
                 (parentObj) -> {
                     parentObj.registerC = parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                     parentObj.registerB = parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF);
                     parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // JP !FZ, nn
                 // #0xC2:
                 (parentObj) -> {
                     if (!parentObj.fZero) {
                         parentObj.programCounter = (parentObj
                                 .memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                 parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                         parentObj.cpuTicks += GBEMU_4;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     }
                 },
                 // JP nn
                 // #0xC3:
                 (parentObj) -> {
                     parentObj.programCounter = (parentObj
                             .memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                             parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                 },
                 // CALL !FZ, nn
                 // #0xC4:
                 (parentObj) -> {
                     if (!parentObj.fZero) {
                         int temp_pc = (parentObj
                                 .memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                 parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                         parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                         parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter >> GBEMU_8);
                         parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                         parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter & GBEMU_0xFF);
                         parentObj.programCounter = temp_pc;
                         parentObj.cpuTicks += GBEMU_12;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     }
                 },
                 // PUSH BC
                 // #0xC5:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.registerB);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.registerC);
                 },
                 // ADD, n
                 // #0xC6:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA + parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) < (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // RST 0
                 // #0xC7:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = 0;
                 },
                 // RET FZ
                 // #0xC8:
                 (parentObj) -> {
                     if (parentObj.fZero) {
                         parentObj.programCounter =
                                 (parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                         parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                         parentObj.cpuTicks += GBEMU_12;
                     }
                 },
                 // RET
                 // #0xC9:
                 (parentObj) -> {
                     parentObj.programCounter =
                             (parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                     parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                     parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // JP FZ, nn
                 // #0xCA:
                 (parentObj) -> {
                     if (parentObj.fZero) {
                         parentObj.programCounter =
                                 (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                         parentObj.cpuTicks += GBEMU_4;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     }
                 },
                 // Secondary OP Code Set:
                 // #0xCB:
                 (parentObj) -> {
                     int opcode = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     // Increment the program counter to the next instruction:
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     // Execute secondary OP codes for the 0xCB OP code call.
                     parentObj.cbOpCode[opcode].call(parentObj);
                     // Get how many CPU cycles the current 0xCBXX op code counts for:
                     parentObj.cpuTicks += parentObj.secondaryTickTable[opcode];
                 },
                 // CALL FZ, nn
                 // #0xCC:
                 (parentObj) -> {
                     if (parentObj.fZero) {
                         int temp_pc =
                                 (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                         parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                         parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter >> GBEMU_8);
                         parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                         parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter & GBEMU_0xFF);
                         parentObj.programCounter = temp_pc;
                         parentObj.cpuTicks += GBEMU_12;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     }
                 },
                 // CALL nn
                 // #0xCD:
                 (parentObj) -> {
                     int temp_pc =
                             (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                     parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = temp_pc;
                 },
                 // ADC A, n
                 // #0xCE:
                 (parentObj) -> {
                     int tempValue = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj,parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     int dirtySum = parentObj.registerA + tempValue + (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) + (tempValue & GBEMU_0xF) + (parentObj.fCarry ? 1 : 0) > GBEMU_0xF;
                     parentObj.fCarry = dirtySum > GBEMU_0xFF;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                 },
                 // RST 0x8
                 // #0xCF:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = 0x8;
                 },
                 // RET !FC
                 // #0xD0:
                 (parentObj) -> {
                     if (!parentObj.fCarry) {
                         parentObj.programCounter =
                                 (parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                         parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                         parentObj.cpuTicks += GBEMU_12;
                     }
                 },
                 // POP DE
                 // #0xD1:
                 (parentObj) -> {
                     parentObj.registerE = parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj,parentObj.stackPointer);
                     parentObj.registerD = parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF);
                     parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // JP !FC, nn
                 // #0xD2:
                 (parentObj) -> {
                     if (!parentObj.fCarry) {
                         parentObj.programCounter =
                                 (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                         parentObj.cpuTicks += GBEMU_4;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     }
                 },
                 // 0xD3 - Illegal
                 // #0xD3:
                 (parentObj) -> {
                     cout("Illegal op code 0xD3 called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // CALL !FC, nn
                 // #0xD4:
                 (parentObj) -> {
                     if (!parentObj.fCarry) {
                         int tempPc =
                                 (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                         parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                         parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter >> GBEMU_8);
                         parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                         parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter & GBEMU_0xFF);
                         parentObj.programCounter = tempPc;
                         parentObj.cpuTicks += GBEMU_12;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     }
                 },
                 // PUSH DE
                 // #0xD5:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.registerD);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.registerE);
                 },
                 // SUB A, n
                 // #0xD6:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) < (dirtySum & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // RST 0x10
                 // #0xD7:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = GBEMU_0x10;
                 },
                 // RET FC
                 // #0xD8:
                 (parentObj) -> {
                     if (parentObj.fCarry) {
                         parentObj.programCounter =
                                 (parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                         parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                         parentObj.cpuTicks += GBEMU_12;
                     }
                 },
                 // RETI
                 // #0xD9:
                 (parentObj) -> {
                     parentObj.programCounter =
                             (parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                     parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                     parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                     // Immediate for HALT:
                     parentObj.irqEnableDelay = parentObj.irqEnableDelay == GBEMU_2 || parentObj.memoryReader
                             .get(parentObj.programCounter).call(parentObj, parentObj.programCounter) == GBEMU_0x76 ?
                             1 :
                             GBEMU_2;
                 },
                 // JP FC, nn
                 // #0xDA:
                 (parentObj) -> {
                     if (parentObj.fCarry) {
                         parentObj.programCounter =
                                 (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                         parentObj.cpuTicks += GBEMU_4;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     }
                 },
                 // 0xDB - Illegal
                 // #0xDB:
                 (parentObj) -> {
                     cout("Illegal op code 0xDB called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // CALL FC, nn
                 // #0xDC:
                 (parentObj) -> {
                     if (parentObj.fCarry) {
                         int tempPc =
                                 (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                         parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                         parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                         parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter >> GBEMU_8);
                         parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                         parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer,parentObj.programCounter & GBEMU_0xFF);
                         parentObj.programCounter = tempPc;
                         parentObj.cpuTicks += GBEMU_12;
                     } else {
                         parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                     }
                 },
                 // 0xDD - Illegal
                 // #0xDD:
                 (parentObj) -> {
                     cout("Illegal op code 0xDD called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // SBC A, n
                 // #0xDE:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     int dirtySum = parentObj.registerA - tempVar - (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = (parentObj.registerA & GBEMU_0xF) - (tempVar & GBEMU_0xF) - (parentObj.fCarry ? 1 : 0) < 0;
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.registerA = dirtySum & GBEMU_0xFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = true;
                 },
                 // RST 0x18
                 // #0xDF:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = GBEMU_0x18;
                 },
                 // LDH (n), A
                 // #0xE0:
                 (parentObj) -> {
                     parentObj.memoryHighWrite(parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter), parentObj.registerA);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // POP HL
                 // #0xE1:
                 (parentObj) -> {
                     parentObj.registersHL =
                             (parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                     parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                     parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // LD (0xFF00 + C), A
                 // #0xE2:
                 (parentObj) -> {
                     parentObj.memoryHighWriter.get(parentObj.registerC).call(parentObj, parentObj.registerC, parentObj.registerA);
                 },
                 // 0xE3 - Illegal
                 // #0xE3:
                 (parentObj) -> {
                     cout("Illegal op code 0xE3 called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // 0xE4 - Illegal
                 // #0xE4:
                 (parentObj) -> {
                     cout("Illegal op code 0xE4 called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // PUSH HL
                 // #0xE5:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.registersHL >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.registersHL & GBEMU_0xFF);
                 },
                 // AND n
                 // #0xE6:
                 (parentObj) -> {
                     parentObj.registerA &= parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                 },
                 // RST 0x20
                 // #0xE7:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = GBEMU_0x20;
                 },
                 // ADD SP, n
                 // #0xE8:
                 (parentObj) -> {
                     int tempValue2 = (parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) << GBEMU_24) >> GBEMU_24;
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     int tempValue = (parentObj.stackPointer + tempValue2) & GBEMU_0xFFFF;
                     tempValue2 = parentObj.stackPointer ^ tempValue2 ^ tempValue;
                     parentObj.stackPointer = tempValue;
                     parentObj.fCarry = (tempValue2 & GBEMU_0x100) == GBEMU_0x100;
                     parentObj.fHalfCarry = (tempValue2 & GBEMU_0x10) == GBEMU_0x10;
                     parentObj.fZero = false;
                     parentObj.fSubtract = false;
                 },
                 // JP, (HL)
                 // #0xE9:
                 (parentObj) -> {
                     parentObj.programCounter = parentObj.registersHL;
                 },
                 // LD n, A
                 // #0xEA:
                 (parentObj) -> {
                     parentObj.memoryWrite(
                             (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                     parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter),
                             parentObj.registerA
                     );
                     parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // 0xEB - Illegal
                 // #0xEB:
                 (parentObj) -> {
                     cout("Illegal op code 0xEB called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // 0xEC - Illegal
                 // #0xEC:
                 (parentObj) -> {
                     cout("Illegal op code 0xEC called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // 0xED - Illegal
                 // #0xED:
                 (parentObj) -> {
                     cout("Illegal op code 0xED called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // XOR n
                 // #0xEE:
                 (parentObj) -> {
                     parentObj.registerA ^= parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fSubtract = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fCarry = false;
                 },
                 // RST 0x28
                 // #0xEF:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = GBEMU_0x28;
                 },
                 // LDH A, (n)
                 // #0xF0:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryHighRead(parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter));
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                 },
                 // POP AF
                 // #0xF1:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer);
                     parentObj.fZero = tempVar > GBEMU_0x7F;
                     parentObj.fSubtract = (tempVar & GBEMU_0x40) == GBEMU_0x40;
                     parentObj.fHalfCarry = (tempVar & GBEMU_0x20) == GBEMU_0x20;
                     parentObj.fCarry = (tempVar & GBEMU_0x10) == GBEMU_0x10;
                     parentObj.registerA = parentObj.memoryRead((parentObj.stackPointer + 1) & GBEMU_0xFFFF);
                     parentObj.stackPointer = (parentObj.stackPointer + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // LD A, (0xFF00 + C)
                 // #0xF2:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryHighReader.get(parentObj.registerC).call(parentObj, parentObj.registerC);
                 },
                 // DI
                 // #0xF3:
                 (parentObj) -> {
                     parentObj.ime = false;
                     parentObj.irqEnableDelay = 0;
                 },
                 // 0xF4 - Illegal
                 // #0xF4:
                 (parentObj) -> {
                     cout("Illegal op code 0xF4 called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // PUSH AF
                 // #0xF5:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.registerA);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(
                             parentObj,
                             parentObj.stackPointer,
                             (parentObj.fZero ? GBEMU_0x80 : 0) |
                                     (parentObj.fSubtract ? GBEMU_0x40 : 0) |
                                     (parentObj.fHalfCarry ? GBEMU_0x20 : 0) |
                                     (parentObj.fCarry ? GBEMU_0x10 : 0)
                     );
                 },
                 // OR n
                 // #0xF6:
                 (parentObj) -> {
                     parentObj.registerA |= parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     parentObj.fSubtract = false;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                 },
                 // RST 0x30
                 // #0xF7:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = GBEMU_0x30;
                 },
                 // LDHL SP, n
                 // #0xF8:
                 (parentObj) -> {
                     int tempVar = (parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) << GBEMU_24) >> GBEMU_24;
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     parentObj.registersHL = (parentObj.stackPointer + tempVar) & GBEMU_0xFFFF;
                     tempVar = parentObj.stackPointer ^ tempVar ^ parentObj.registersHL;
                     parentObj.fCarry = (tempVar & GBEMU_0x100) == GBEMU_0x100;
                     parentObj.fHalfCarry = (tempVar & GBEMU_0x10) == GBEMU_0x10;
                     parentObj.fZero = false;
                     parentObj.fSubtract = false;
                 },
                 // LD SP, HL
                 // #0xF9:
                 (parentObj) -> {
                     parentObj.stackPointer = parentObj.registersHL;
                 },
                 // LD A, (nn)
                 // #0xFA:
                 (parentObj) -> {
                     parentObj.registerA = parentObj.memoryRead(
                             (parentObj.memoryRead((parentObj.programCounter + 1) & GBEMU_0xFFFF) << GBEMU_8) |
                                     parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter
                                     ));
                     parentObj.programCounter = (parentObj.programCounter + GBEMU_2) & GBEMU_0xFFFF;
                 },
                 // EI
                 // #0xFB:
                 (parentObj) -> {
                     // Immediate for HALT:
                     parentObj.irqEnableDelay =
                             parentObj.irqEnableDelay == GBEMU_2 || parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter) == GBEMU_0x76 ?
                                     1 :
                                     GBEMU_2;
                 },
                 // 0xFC - Illegal
                 // #0xFC:
                 (parentObj) -> {
                     cout("Illegal op code 0xFC called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // 0xFD - Illegal
                 // #0xFD:
                 (parentObj) -> {
                     cout("Illegal op code 0xFD called, pausing emulation.", GBEMU_2);
                     pausePlay();
                 },
                 // CP n
                 // #0xFE:
                 (parentObj) -> {
                     int dirtySum = parentObj.registerA - parentObj.memoryReader.get(parentObj.programCounter).call(parentObj, parentObj.programCounter);
                     parentObj.programCounter = (parentObj.programCounter + 1) & GBEMU_0xFFFF;
                     parentObj.fHalfCarry = (dirtySum & GBEMU_0xF) > (parentObj.registerA & GBEMU_0xF);
                     parentObj.fCarry = dirtySum < 0;
                     parentObj.fZero = dirtySum == 0;
                     parentObj.fSubtract = true;
                 },
                 // RST 0x38
                 // #0xFF:
                 (parentObj) -> {
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter >> GBEMU_8);
                     parentObj.stackPointer = (parentObj.stackPointer - 1) & GBEMU_0xFFFF;
                     parentObj.memoryWriter.get(parentObj.stackPointer).call(parentObj, parentObj.stackPointer, parentObj.programCounter & GBEMU_0xFF);
                     parentObj.programCounter = GBEMU_0x38;
                 }
         };
         public GbemuPartCodeFun[] cbOpCode = new GbemuPartCodeFun[] {
                 // RLC B
                 // #0x00:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerB > GBEMU_0x7F;
                     parentObj.registerB = ((parentObj.registerB << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerB == 0;
                 },
                 // RLC C
                 // #0x01:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerC > GBEMU_0x7F;
                     parentObj.registerC = ((parentObj.registerC << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerC == 0;
                 },
                 // RLC D
                 // #0x02:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerD > GBEMU_0x7F;
                     parentObj.registerD = ((parentObj.registerD << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerD == 0;
                 },
                 // RLC E
                 // #0x03:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerE > GBEMU_0x7F;
                     parentObj.registerE = ((parentObj.registerE << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerE == 0;
                 },
                 // RLC H
                 // #0x04:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registersHL > GBEMU_0x7FFF;
                     parentObj.registersHL = ((parentObj.registersHL << 1) & GBEMU_0xFE00) | (parentObj.fCarry ? GBEMU_0x100 : 0) | (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registersHL < GBEMU_0x100;
                 },
                 // RLC L
                 // #0x05:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registersHL & GBEMU_0x80) == GBEMU_0x80;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | ((parentObj.registersHL << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0xFF) == 0;
                 },
                 // RLC (HL)
                 // #0x06:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fCarry = tempVar > GBEMU_0x7F;
                     tempVar = ((tempVar << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = tempVar == 0;
                 },
                 // RLC A
                 // #0x07:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerA > GBEMU_0x7F;
                     parentObj.registerA = ((parentObj.registerA << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerA == 0;
                 },
                 // RRC B
                 // #0x08:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerB & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerB = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerB >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerB == 0;
                 },
                 // RRC C
                 // #0x09:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerC & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerC = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerC >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerC == 0;
                 },
                 // RRC D
                 // #0x0A:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerD & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerD = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerD >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerD == 0;
                 },
                 // RRC E
                 // #0x0B:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerE & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerE = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerE >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerE == 0;
                 },
                 // RRC H
                 // #0x0C:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registersHL & GBEMU_0x0100) == GBEMU_0x0100;
                     parentObj.registersHL = (parentObj.fCarry ? GBEMU_0x8000 : 0) | ((parentObj.registersHL >> 1) & GBEMU_0xFF00) | (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registersHL < GBEMU_0x100;
                 },
                 // RRC L
                 // #0x0D:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registersHL & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | (parentObj.fCarry ? GBEMU_0x80 : 0) | ((parentObj.registersHL & GBEMU_0xFF) >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0xFF) == 0;
                 },
                 // RRC (HL)
                 // #0x0E:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fCarry = (tempVar & GBEMU_0x01) == GBEMU_0x01;
                     tempVar = (parentObj.fCarry ? GBEMU_0x80 : 0) | (tempVar >> 1);
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = tempVar == 0;
                 },
                 // RRC A
                 // #0x0F:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerA & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerA = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerA >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerA == 0;
                 },
                 // RL B
                 // #0x10:
                 (parentObj) -> {
                     boolean newfCarry = parentObj.registerB > GBEMU_0x7F;
                     parentObj.registerB = ((parentObj.registerB << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerB == 0;
                 },
                 // RL C
                 // #0x11:
                 (parentObj) -> {
                     boolean newfCarry = parentObj.registerC > GBEMU_0x7F;
                     parentObj.registerC = ((parentObj.registerC << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerC == 0;
                 },
                 // RL D
                 // #0x12:
                 (parentObj) -> {
                     boolean newfCarry = parentObj.registerD > GBEMU_0x7F;
                     parentObj.registerD = ((parentObj.registerD << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerD == 0;
                 },
                 // RL E
                 // #0x13:
                 (parentObj) -> {
                     boolean newfCarry = parentObj.registerE > GBEMU_0x7F;
                     parentObj.registerE = ((parentObj.registerE << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerE == 0;
                 },
                 // RL H
                 // #0x14:
                 (parentObj) -> {
                     boolean newfCarry = parentObj.registersHL > GBEMU_0x7FFF;
                     parentObj.registersHL = ((parentObj.registersHL << 1) & GBEMU_0xFE00) | (parentObj.fCarry ? GBEMU_0x100 : 0) | (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registersHL < GBEMU_0x100;
                 },
                 // RL L
                 // #0x15:
                 (parentObj) -> {
                     boolean newfCarry = (parentObj.registersHL & GBEMU_0x80) == GBEMU_0x80;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | ((parentObj.registersHL << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0xFF) == 0;
                 },
                 // RL (HL)
                 // #0x16:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     boolean newfCarry = tempVar > GBEMU_0x7F;
                     tempVar = ((tempVar << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fCarry = newfCarry;
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = tempVar == 0;
                 },
                 // RL A
                 // #0x17:
                 (parentObj) -> {
                     boolean newfCarry = parentObj.registerA > GBEMU_0x7F;
                     parentObj.registerA = ((parentObj.registerA << 1) & GBEMU_0xFF) | (parentObj.fCarry ? 1 : 0);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerA == 0;
                 },
                 // RR B
                 // #0x18:
                 (parentObj) -> {
                     boolean newfCarry = (parentObj.registerB & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerB = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerB >> 1);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerB == 0;
                 },
                 // RR C
                 // #0x19:
                 (parentObj) -> {
                     boolean newfCarry = (parentObj.registerC & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerC = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerC >> 1);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerC == 0;
                 },
                 // RR D
                 // #0x1A:
                 (parentObj) -> {
                     boolean newfCarry = (parentObj.registerD & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerD = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerD >> 1);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerD == 0;
                 },
                 // RR E
                 // #0x1B:
                 (parentObj) -> {
                     boolean newfCarry = (parentObj.registerE & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerE = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerE >> 1);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerE == 0;
                 },
                 // RR H
                 // #0x1C:
                 (parentObj) -> {
                     boolean newfCarry = (parentObj.registersHL & GBEMU_0x0100) == GBEMU_0x0100;
                     parentObj.registersHL = (parentObj.fCarry ? GBEMU_0x8000 : 0) | ((parentObj.registersHL >> 1) & GBEMU_0xFF00) | (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registersHL < GBEMU_0x100;
                 },
                 // RR L
                 // #0x1D:
                 (parentObj) -> {
                     boolean newfCarry = (parentObj.registersHL & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | (parentObj.fCarry ? GBEMU_0x80 : 0) | ((parentObj.registersHL & GBEMU_0xFF) >> 1);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0xFF) == 0;
                 },
                 // RR (HL)
                 // #0x1E:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     boolean newfCarry = (tempVar & GBEMU_0x01) == GBEMU_0x01;
                     tempVar = (parentObj.fCarry ? GBEMU_0x80 : 0) | (tempVar >> 1);
                     parentObj.fCarry = newfCarry;
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = tempVar == 0;
                 },
                 // RR A
                 // #0x1F:
                 (parentObj) -> {
                     boolean newfCarry = (parentObj.registerA & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerA = (parentObj.fCarry ? GBEMU_0x80 : 0) | (parentObj.registerA >> 1);
                     parentObj.fCarry = newfCarry;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerA == 0;
                 },
                 // SLA B
                 // #0x20:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerB > GBEMU_0x7F;
                     parentObj.registerB = (parentObj.registerB << 1) & GBEMU_0xFF;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerB == 0;
                 },
                 // SLA C
                 // #0x21:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerC > GBEMU_0x7F;
                     parentObj.registerC = (parentObj.registerC << 1) & GBEMU_0xFF;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerC == 0;
                 },
                 // SLA D
                 // #0x22:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerD > GBEMU_0x7F;
                     parentObj.registerD = (parentObj.registerD << 1) & GBEMU_0xFF;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerD == 0;
                 },
                 // SLA E
                 // #0x23:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerE > GBEMU_0x7F;
                     parentObj.registerE = (parentObj.registerE << 1) & GBEMU_0xFF;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerE == 0;
                 },
                 // SLA H
                 // #0x24:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registersHL > GBEMU_0x7FFF;
                     parentObj.registersHL = ((parentObj.registersHL << 1) & GBEMU_0xFE00) | (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registersHL < GBEMU_0x100;
                 },
                 // SLA L
                 // #0x25:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registersHL & GBEMU_0x0080) == GBEMU_0x0080;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | ((parentObj.registersHL << 1) & GBEMU_0xFF);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0xFF) == 0;
                 },
                 // SLA (HL)
                 // #0x26:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fCarry = tempVar > GBEMU_0x7F;
                     tempVar = (tempVar << 1) & GBEMU_0xFF;
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = tempVar == 0;
                 },
                 // SLA A
                 // #0x27:
                 (parentObj) -> {
                     parentObj.fCarry = parentObj.registerA > GBEMU_0x7F;
                     parentObj.registerA = (parentObj.registerA << 1) & GBEMU_0xFF;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerA == 0;
                 },
                 // SRA B
                 // #0x28:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerB & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerB = (parentObj.registerB & GBEMU_0x80) | (parentObj.registerB >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerB == 0;
                 },
                 // SRA C
                 // #0x29:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerC & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerC = (parentObj.registerC & GBEMU_0x80) | (parentObj.registerC >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerC == 0;
                 },
                 // SRA D
                 // #0x2A:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerD & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerD = (parentObj.registerD & GBEMU_0x80) | (parentObj.registerD >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerD == 0;
                 },
                 // SRA E
                 // #0x2B:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerE & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerE = (parentObj.registerE & GBEMU_0x80) | (parentObj.registerE >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerE == 0;
                 },
                 // SRA H
                 // #0x2C:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registersHL & GBEMU_0x0100) == GBEMU_0x0100;
                     parentObj.registersHL = ((parentObj.registersHL >> 1) & GBEMU_0xFF00) | (parentObj.registersHL & GBEMU_0x80FF);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registersHL < GBEMU_0x100;
                 },
                 // SRA L
                 // #0x2D:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registersHL & GBEMU_0x0001) == GBEMU_0x0001;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF80) | ((parentObj.registersHL & GBEMU_0xFF) >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0xFF) == 0;
                 },
                 // SRA (HL)
                 // #0x2E:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fCarry = (tempVar & GBEMU_0x01) == GBEMU_0x01;
                     tempVar = (tempVar & GBEMU_0x80) | (tempVar >> 1);
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = tempVar == 0;
                 },
                 // SRA A
                 // #0x2F:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerA & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerA = (parentObj.registerA & GBEMU_0x80) | (parentObj.registerA >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerA == 0;
                 },
                 // SWAP B
                 // #0x30:
                 (parentObj) -> {
                     parentObj.registerB = ((parentObj.registerB & GBEMU_0xF) << GBEMU_4) | (parentObj.registerB >> GBEMU_4);
                     parentObj.fZero = parentObj.registerB == 0;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                 },
                 // SWAP C
                 // #0x31:
                 (parentObj) -> {
                     parentObj.registerC = ((parentObj.registerC & GBEMU_0xF) << GBEMU_4) | (parentObj.registerC >> GBEMU_4);
                     parentObj.fZero = parentObj.registerC == 0;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                 },
                 // SWAP D
                 // #0x32:
                 (parentObj) -> {
                     parentObj.registerD = ((parentObj.registerD & GBEMU_0xF) << GBEMU_4) | (parentObj.registerD >> GBEMU_4);
                     parentObj.fZero = parentObj.registerD == 0;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                 },
                 // SWAP E
                 // #0x33:
                 (parentObj) -> {
                     parentObj.registerE = ((parentObj.registerE & GBEMU_0xF) << GBEMU_4) | (parentObj.registerE >> GBEMU_4);
                     parentObj.fZero = parentObj.registerE == 0;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                 },
                 // SWAP H
                 // #0x34:
                 (parentObj) -> {
                     parentObj.registersHL =
                             ((parentObj.registersHL & GBEMU_0xF00) << GBEMU_4) | ((parentObj.registersHL & GBEMU_0xF000) >> GBEMU_4) | (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fZero = parentObj.registersHL < GBEMU_0x100;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                 },
                 // SWAP L
                 // #0x35:
                 (parentObj) -> {
                     parentObj.registersHL =
                             (parentObj.registersHL & GBEMU_0xFF00) | ((parentObj.registersHL & GBEMU_0xF) << GBEMU_4) | ((parentObj.registersHL & GBEMU_0xF0) >> GBEMU_4);
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0xFF) == 0;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                 },
                 // SWAP (HL)
                 // #0x36:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     tempVar = ((tempVar & GBEMU_0xF) << GBEMU_4) | (tempVar >> GBEMU_4);
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar);
                     parentObj.fZero = tempVar == 0;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                 },
                 // SWAP A
                 // #0x37:
                 (parentObj) -> {
                     parentObj.registerA = ((parentObj.registerA & GBEMU_0xF) << GBEMU_4) | (parentObj.registerA >> GBEMU_4);
                     parentObj.fZero = parentObj.registerA == 0;
                     parentObj.fCarry = false;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                 },
                 // SRL B
                 // #0x38:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerB & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerB >>= 1;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerB == 0;
                 },
                 // SRL C
                 // #0x39:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerC & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerC >>= 1;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerC == 0;
                 },
                 // SRL D
                 // #0x3A:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerD & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerD >>= 1;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerD == 0;
                 },
                 // SRL E
                 // #0x3B:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerE & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerE >>= 1;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerE == 0;
                 },
                 // SRL H
                 // #0x3C:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registersHL & GBEMU_0x0100) == GBEMU_0x0100;
                     parentObj.registersHL = ((parentObj.registersHL >> 1) & GBEMU_0xFF00) | (parentObj.registersHL & GBEMU_0xFF);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registersHL < GBEMU_0x100;
                 },
                 // SRL L
                 // #0x3D:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registersHL & GBEMU_0x0001) == GBEMU_0x0001;
                     parentObj.registersHL = (parentObj.registersHL & GBEMU_0xFF00) | ((parentObj.registersHL & GBEMU_0xFF) >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0xFF) == 0;
                 },
                 // SRL (HL)
                 // #0x3E:
                 (parentObj) -> {
                     int tempVar = parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL);
                     parentObj.fCarry = (tempVar & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.memoryWriter.get(parentObj.registersHL).call(parentObj, parentObj.registersHL, tempVar >> 1);
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = tempVar < GBEMU_2;
                 },
                 // SRL A
                 // #0x3F:
                 (parentObj) -> {
                     parentObj.fCarry = (parentObj.registerA & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.registerA >>= 1;
                     parentObj.fHalfCarry = false;
                     parentObj.fSubtract = false;
                     parentObj.fZero = parentObj.registerA == 0;
                 },
                 // BIT 0, B
                 // #0x40:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerB & GBEMU_0x01) == 0;
                 },
                 // BIT 0, C
                 // #0x41:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerC & GBEMU_0x01) == 0;
                 },
                 // BIT 0, D
                 // #0x42:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerD & GBEMU_0x01) == 0;
                 },
                 // BIT 0, E
                 // #0x43:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerE & GBEMU_0x01) == 0;
                 },
                 // BIT 0, H
                 // #0x44:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0100) == 0;
                 },
                 // BIT 0, L
                 // #0x45:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0001) == 0;
                 },
                 // BIT 0, (HL)
                 // #0x46:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL)  & GBEMU_0x01) == 0;
                 },
                 // BIT 0, A
                 // #0x47:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerA & GBEMU_0x01) == 0;
                 },
                 // BIT 1, B
                 // #0x48:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerB & GBEMU_0x02) == 0;
                 },
                 // BIT 1, C
                 // #0x49:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerC & GBEMU_0x02) == 0;
                 },
                 // BIT 1, D
                 // #0x4A:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerD & GBEMU_0x02) == 0;
                 },
                 // BIT 1, E
                 // #0x4B:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerE & GBEMU_0x02) == 0;
                 },
                 // BIT 1, H
                 // #0x4C:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0200) == 0;
                 },
                 // BIT 1, L
                 // #0x4D:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0002) == 0;
                 },
                 // BIT 1, (HL)
                 // #0x4E:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL)  & GBEMU_0x02) == 0;
                 },
                 // BIT 1, A
                 // #0x4F:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerA & GBEMU_0x02) == 0;
                 },
                 // BIT GBEMU_2, B
                 // #0x50:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerB & GBEMU_0x04) == 0;
                 },
                 // BIT GBEMU_2, C
                 // #0x51:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerC & GBEMU_0x04) == 0;
                 },
                 // BIT GBEMU_2, D
                 // #0x52:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerD & GBEMU_0x04) == 0;
                 },
                 // BIT GBEMU_2, E
                 // #0x53:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerE & GBEMU_0x04) == 0;
                 },
                 // BIT GBEMU_2, H
                 // #0x54:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0400) == 0;
                 },
                 // BIT GBEMU_2, L
                 // #0x55:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0004) == 0;
                 },
                 // BIT GBEMU_2, (HL)
                 // #0x56:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0x04) == 0;
                 },
                 // BIT GBEMU_2, A
                 // #0x57:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerA & GBEMU_0x04) == 0;
                 },
                 // BIT GBEMU_3, B
                 // #0x58:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerB & GBEMU_0x08) == 0;
                 },
                 // BIT GBEMU_3, C
                 // #0x59:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerC & GBEMU_0x08) == 0;
                 },
                 // BIT GBEMU_3, D
                 // #0x5A:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerD & GBEMU_0x08) == 0;
                 },
                 // BIT GBEMU_3, E
                 // #0x5B:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerE & GBEMU_0x08) == 0;
                 },
                 // BIT GBEMU_3, H
                 // #0x5C:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0800) == 0;
                 },
                 // BIT GBEMU_3, L
                 // #0x5D:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0008) == 0;
                 },
                 // BIT GBEMU_3, (HL)
                 // #0x5E:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0x08) == 0;
                 },
                 // BIT GBEMU_3, A
                 // #0x5F:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerA & GBEMU_0x08) == 0;
                 },
                 // BIT GBEMU_4, B
                 // #0x60:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerB & GBEMU_0x10) == 0;
                 },
                 // BIT GBEMU_4, C
                 // #0x61:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerC & GBEMU_0x10) == 0;
                 },
                 // BIT GBEMU_4, D
                 // #0x62:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerD & GBEMU_0x10) == 0;
                 },
                 // BIT GBEMU_4, E
                 // #0x63:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerE & GBEMU_0x10) == 0;
                 },
                 // BIT GBEMU_4, H
                 // #0x64:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x1000) == 0;
                 },
                 // BIT GBEMU_4, L
                 // #0x65:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0010) == 0;
                 },
                 // BIT GBEMU_4, (HL)
                 // #0x66:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0x10) == 0;
                 },
                 // BIT GBEMU_4, A
                 // #0x67:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerA & GBEMU_0x10) == 0;
                 },
                 // BIT GBEMU_5, B
                 // #0x68:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerB & GBEMU_0x20) == 0;
                 },
                 // BIT GBEMU_5, C
                 // #0x69:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerC & GBEMU_0x20) == 0;
                 },
                 // BIT GBEMU_5, D
                 // #0x6A:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerD & GBEMU_0x20) == 0;
                 },
                 // BIT GBEMU_5, E
                 // #0x6B:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerE & GBEMU_0x20) == 0;
                 },
                 // BIT GBEMU_5, H
                 // #0x6C:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x2000) == 0;
                 },
                 // BIT GBEMU_5, L
                 // #0x6D:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0020) == 0;
                 },
                 // BIT GBEMU_5, (HL)
                 // #0x6E:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0x20) == 0;
                 },
                 // BIT GBEMU_5, A
                 // #0x6F:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerA & GBEMU_0x20) == 0;
                 },
                 // BIT GBEMU_6, B
                 // #0x70:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerB & GBEMU_0x40) == 0;
                 },
                 // BIT GBEMU_6, C
                 // #0x71:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerC & GBEMU_0x40) == 0;
                 },
                 // BIT GBEMU_6, D
                 // #0x72:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerD & GBEMU_0x40) == 0;
                 },
                 // BIT GBEMU_6, E
                 // #0x73:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerE & GBEMU_0x40) == 0;
                 },
                 // BIT GBEMU_6, H
                 // #0x74:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x4000) == 0;
                 },
                 // BIT GBEMU_6, L
                 // #0x75:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0040) == 0;
                 },
                 // BIT GBEMU_6, (HL)
                 // #0x76:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0x40) == 0;
                 },
                 // BIT GBEMU_6, A
                 // #0x77:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerA & GBEMU_0x40) == 0;
                 },
                 // BIT GBEMU_7, B
                 // #0x78:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerB & GBEMU_0x80) == 0;
                 },
                 // BIT GBEMU_7, C
                 // #0x79:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerC & GBEMU_0x80) == 0;
                 },
                 // BIT GBEMU_7, D
                 // #0x7A:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerD & GBEMU_0x80) == 0;
                 },
                 // BIT GBEMU_7, E
                 // #0x7B:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerE & GBEMU_0x80) == 0;
                 },
                 // BIT GBEMU_7, H
                 // #0x7C:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x8000) == 0;
                 },
                 // BIT GBEMU_7, L
                 // #0x7D:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registersHL & GBEMU_0x0080) == 0;
                 },
                 // BIT GBEMU_7, (HL)
                 // #0x7E:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0x80) == 0;
                 },
                 // BIT GBEMU_7, A
                 // #0x7F:
                 (parentObj) -> {
                     parentObj.fHalfCarry = true;
                     parentObj.fSubtract = false;
                     parentObj.fZero = (parentObj.registerA & GBEMU_0x80) == 0;
                 },
                 // RES 0, B
                 // #0x80:
                 (parentObj) -> {
                     parentObj.registerB &= GBEMU_0xFE;
                 },
                 // RES 0, C
                 // #0x81:
                 (parentObj) -> {
                     parentObj.registerC &= GBEMU_0xFE;
                 },
                 // RES 0, D
                 // #0x82:
                 (parentObj) -> {
                     parentObj.registerD &= GBEMU_0xFE;
                 },
                 // RES 0, E
                 // #0x83:
                 (parentObj) -> {
                     parentObj.registerE &= GBEMU_0xFE;
                 },
                 // RES 0, H
                 // #0x84:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFEFF;
                 },
                 // RES 0, L
                 // #0x85:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFFFE;
                 },
                 // RES 0, (HL)
                 // #0x86:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0xFE
                     );
                 },
                 // RES 0, A
                 // #0x87:
                 (parentObj) -> {
                     parentObj.registerA &= GBEMU_0xFE;
                 },
                 // RES 1, B
                 // #0x88:
                 (parentObj) -> {
                     parentObj.registerB &= GBEMU_0xFD;
                 },
                 // RES 1, C
                 // #0x89:
                 (parentObj) -> {
                     parentObj.registerC &= GBEMU_0xFD;
                 },
                 // RES 1, D
                 // #0x8A:
                 (parentObj) -> {
                     parentObj.registerD &= GBEMU_0xFD;
                 },
                 // RES 1, E
                 // #0x8B:
                 (parentObj) -> {
                     parentObj.registerE &= GBEMU_0xFD;
                 },
                 // RES 1, H
                 // #0x8C:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFDFF;
                 },
                 // RES 1, L
                 // #0x8D:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFFFD;
                 },
                 // RES 1, (HL)
                 // #0x8E:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0xFD
                     );
                 },
                 // RES 1, A
                 // #0x8F:
                 (parentObj) -> {
                     parentObj.registerA &= GBEMU_0xFD;
                 },
                 // RES GBEMU_2, B
                 // #0x90:
                 (parentObj) -> {
                     parentObj.registerB &= GBEMU_0xFB;
                 },
                 // RES GBEMU_2, C
                 // #0x91:
                 (parentObj) -> {
                     parentObj.registerC &= GBEMU_0xFB;
                 },
                 // RES GBEMU_2, D
                 // #0x92:
                 (parentObj) -> {
                     parentObj.registerD &= GBEMU_0xFB;
                 },
                 // RES GBEMU_2, E
                 // #0x93:
                 (parentObj) -> {
                     parentObj.registerE &= GBEMU_0xFB;
                 },
                 // RES GBEMU_2, H
                 // #0x94:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFBFF;
                 },
                 // RES GBEMU_2, L
                 // #0x95:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFFFB;
                 },
                 // RES GBEMU_2, (HL)
                 // #0x96:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0xFB
                     );
                 },
                 // RES GBEMU_2, A
                 // #0x97:
                 (parentObj) -> {
                     parentObj.registerA &= GBEMU_0xFB;
                 },
                 // RES GBEMU_3, B
                 // #0x98:
                 (parentObj) -> {
                     parentObj.registerB &= GBEMU_0xF7;
                 },
                 // RES GBEMU_3, C
                 // #0x99:
                 (parentObj) -> {
                     parentObj.registerC &= GBEMU_0xF7;
                 },
                 // RES GBEMU_3, D
                 // #0x9A:
                 (parentObj) -> {
                     parentObj.registerD &= GBEMU_0xF7;
                 },
                 // RES GBEMU_3, E
                 // #0x9B:
                 (parentObj) -> {
                     parentObj.registerE &= GBEMU_0xF7;
                 },
                 // RES GBEMU_3, H
                 // #0x9C:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xF7FF;
                 },
                 // RES GBEMU_3, L
                 // #0x9D:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFFF7;
                 },
                 // RES GBEMU_3, (HL)
                 // #0x9E:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0xF7
                     );
                 },
                 // RES GBEMU_3, A
                 // #0x9F:
                 (parentObj) -> {
                     parentObj.registerA &= GBEMU_0xF7;
                 },
                 // RES GBEMU_3, B
                 // #0xA0:
                 (parentObj) -> {
                     parentObj.registerB &= GBEMU_0xEF;
                 },
                 // RES GBEMU_4, C
                 // #0xA1:
                 (parentObj) -> {
                     parentObj.registerC &= GBEMU_0xEF;
                 },
                 // RES GBEMU_4, D
                 // #0xA2:
                 (parentObj) -> {
                     parentObj.registerD &= GBEMU_0xEF;
                 },
                 // RES GBEMU_4, E
                 // #0xA3:
                 (parentObj) -> {
                     parentObj.registerE &= GBEMU_0xEF;
                 },
                 // RES GBEMU_4, H
                 // #0xA4:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xEFFF;
                 },
                 // RES GBEMU_4, L
                 // #0xA5:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFFEF;
                 },
                 // RES GBEMU_4, (HL)
                 // #0xA6:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0xEF
                     );
                 },
                 // RES GBEMU_4, A
                 // #0xA7:
                 (parentObj) -> {
                     parentObj.registerA &= GBEMU_0xEF;
                 },
                 // RES GBEMU_5, B
                 // #0xA8:
                 (parentObj) -> {
                     parentObj.registerB &= GBEMU_0xDF;
                 },
                 // RES GBEMU_5, C
                 // #0xA9:
                 (parentObj) -> {
                     parentObj.registerC &= GBEMU_0xDF;
                 },
                 // RES GBEMU_5, D
                 // #0xAA:
                 (parentObj) -> {
                     parentObj.registerD &= GBEMU_0xDF;
                 },
                 // RES GBEMU_5, E
                 // #0xAB:
                 (parentObj) -> {
                     parentObj.registerE &= GBEMU_0xDF;
                 },
                 // RES GBEMU_5, H
                 // #0xAC:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xDFFF;
                 },
                 // RES GBEMU_5, L
                 // #0xAD:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFFDF;
                 },
                 // RES GBEMU_5, (HL)
                 // #0xAE:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0xDF
                     );
                 },
                 // RES GBEMU_5, A
                 // #0xAF:
                 (parentObj) -> {
                     parentObj.registerA &= GBEMU_0xDF;
                 },
                 // RES GBEMU_6, B
                 // #0xB0:
                 (parentObj) -> {
                     parentObj.registerB &= GBEMU_0xBF;
                 },
                 // RES GBEMU_6, C
                 // #0xB1:
                 (parentObj) -> {
                     parentObj.registerC &= GBEMU_0xBF;
                 },
                 // RES GBEMU_6, D
                 // #0xB2:
                 (parentObj) -> {
                     parentObj.registerD &= GBEMU_0xBF;
                 },
                 // RES GBEMU_6, E
                 // #0xB3:
                 (parentObj) -> {
                     parentObj.registerE &= GBEMU_0xBF;
                 },
                 // RES GBEMU_6, H
                 // #0xB4:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xBFFF;
                 },
                 // RES GBEMU_6, L
                 // #0xB5:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFFBF;
                 },
                 // RES GBEMU_6, (HL)
                 // #0xB6:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0xBF
                     );
                 },
                 // RES GBEMU_6, A
                 // #0xB7:
                 (parentObj) -> {
                     parentObj.registerA &= GBEMU_0xBF;
                 },
                 // RES GBEMU_7, B
                 // #0xB8:
                 (parentObj) -> {
                     parentObj.registerB &= GBEMU_0x7F;
                 },
                 // RES GBEMU_7, C
                 // #0xB9:
                 (parentObj) -> {
                     parentObj.registerC &= GBEMU_0x7F;
                 },
                 // RES GBEMU_7, D
                 // #0xBA:
                 (parentObj) -> {
                     parentObj.registerD &= GBEMU_0x7F;
                 },
                 // RES GBEMU_7, E
                 // #0xBB:
                 (parentObj) -> {
                     parentObj.registerE &= GBEMU_0x7F;
                 },
                 // RES GBEMU_7, H
                 // #0xBC:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0x7FFF;
                 },
                 // RES GBEMU_7, L
                 // #0xBD:
                 (parentObj) -> {
                     parentObj.registersHL &= GBEMU_0xFF7F;
                 },
                 // RES GBEMU_7, (HL)
                 // #0xBE:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) & GBEMU_0x7F
                     );
                 },
                 // RES GBEMU_7, A
                 // #0xBF:
                 (parentObj) -> {
                     parentObj.registerA &= GBEMU_0x7F;
                 },
                 // SET 0, B
                 // #0xC0:
                 (parentObj) -> {
                     parentObj.registerB |= GBEMU_0x01;
                 },
                 // SET 0, C
                 // #0xC1:
                 (parentObj) -> {
                     parentObj.registerC |= GBEMU_0x01;
                 },
                 // SET 0, D
                 // #0xC2:
                 (parentObj) -> {
                     parentObj.registerD |= GBEMU_0x01;
                 },
                 // SET 0, E
                 // #0xC3:
                 (parentObj) -> {
                     parentObj.registerE |= GBEMU_0x01;
                 },
                 // SET 0, H
                 // #0xC4:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x0100;
                 },
                 // SET 0, L
                 // #0xC5:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x01;
                 },
                 // SET 0, (HL)
                 // #0xC6:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) | GBEMU_0x01
                     );
                 },
                 // SET 0, A
                 // #0xC7:
                 (parentObj) -> {
                     parentObj.registerA |= GBEMU_0x01;
                 },
                 // SET 1, B
                 // #0xC8:
                 (parentObj) -> {
                     parentObj.registerB |= GBEMU_0x02;
                 },
                 // SET 1, C
                 // #0xC9:
                 (parentObj) -> {
                     parentObj.registerC |= GBEMU_0x02;
                 },
                 // SET 1, D
                 // #0xCA:
                 (parentObj) -> {
                     parentObj.registerD |= GBEMU_0x02;
                 },
                 // SET 1, E
                 // #0xCB:
                 (parentObj) -> {
                     parentObj.registerE |= GBEMU_0x02;
                 },
                 // SET 1, H
                 // #0xCC:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x0200;
                 },
                 // SET 1, L
                 // #0xCD:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x02;
                 },
                 // SET 1, (HL)
                 // #0xCE:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) | GBEMU_0x02
                     );
                 },
                 // SET 1, A
                 // #0xCF:
                 (parentObj) -> {
                     parentObj.registerA |= GBEMU_0x02;
                 },
                 // SET GBEMU_2, B
                 // #0xD0:
                 (parentObj) -> {
                     parentObj.registerB |= GBEMU_0x04;
                 },
                 // SET GBEMU_2, C
                 // #0xD1:
                 (parentObj) -> {
                     parentObj.registerC |= GBEMU_0x04;
                 },
                 // SET GBEMU_2, D
                 // #0xD2:
                 (parentObj) -> {
                     parentObj.registerD |= GBEMU_0x04;
                 },
                 // SET GBEMU_2, E
                 // #0xD3:
                 (parentObj) -> {
                     parentObj.registerE |= GBEMU_0x04;
                 },
                 // SET GBEMU_2, H
                 // #0xD4:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x0400;
                 },
                 // SET GBEMU_2, L
                 // #0xD5:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x04;
                 },
                 // SET GBEMU_2, (HL)
                 // #0xD6:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) | GBEMU_0x04
                     );
                 },
                 // SET GBEMU_2, A
                 // #0xD7:
                 (parentObj) -> {
                     parentObj.registerA |= GBEMU_0x04;
                 },
                 // SET GBEMU_3, B
                 // #0xD8:
                 (parentObj) -> {
                     parentObj.registerB |= GBEMU_0x08;
                 },
                 // SET GBEMU_3, C
                 // #0xD9:
                 (parentObj) -> {
                     parentObj.registerC |= GBEMU_0x08;
                 },
                 // SET GBEMU_3, D
                 // #0xDA:
                 (parentObj) -> {
                     parentObj.registerD |= GBEMU_0x08;
                 },
                 // SET GBEMU_3, E
                 // #0xDB:
                 (parentObj) -> {
                     parentObj.registerE |= GBEMU_0x08;
                 },
                 // SET GBEMU_3, H
                 // #0xDC:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x0800;
                 },
                 // SET GBEMU_3, L
                 // #0xDD:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x08;
                 },
                 // SET GBEMU_3, (HL)
                 // #0xDE:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) | GBEMU_0x08
                     );
                 },
                 // SET GBEMU_3, A
                 // #0xDF:
                 (parentObj) -> {
                     parentObj.registerA |= GBEMU_0x08;
                 },
                 // SET GBEMU_4, B
                 // #0xE0:
                 (parentObj) -> {
                     parentObj.registerB |= GBEMU_0x10;
                 },
                 // SET GBEMU_4, C
                 // #0xE1:
                 (parentObj) -> {
                     parentObj.registerC |= GBEMU_0x10;
                 },
                 // SET GBEMU_4, D
                 // #0xE2:
                 (parentObj) -> {
                     parentObj.registerD |= GBEMU_0x10;
                 },
                 // SET GBEMU_4, E
                 // #0xE3:
                 (parentObj) -> {
                     parentObj.registerE |= GBEMU_0x10;
                 },
                 // SET GBEMU_4, H
                 // #0xE4:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x1000;
                 },
                 // SET GBEMU_4, L
                 // #0xE5:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x10;
                 },
                 // SET GBEMU_4, (HL)
                 // #0xE6:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) | GBEMU_0x10
                     );
                 },
                 // SET GBEMU_4, A
                 // #0xE7:
                 (parentObj) -> {
                     parentObj.registerA |= GBEMU_0x10;
                 },
                 // SET GBEMU_5, B
                 // #0xE8:
                 (parentObj) -> {
                     parentObj.registerB |= GBEMU_0x20;
                 },
                 // SET GBEMU_5, C
                 // #0xE9:
                 (parentObj) -> {
                     parentObj.registerC |= GBEMU_0x20;
                 },
                 // SET GBEMU_5, D
                 // #0xEA:
                 (parentObj) -> {
                     parentObj.registerD |= GBEMU_0x20;
                 },
                 // SET GBEMU_5, E
                 // #0xEB:
                 (parentObj) -> {
                     parentObj.registerE |= GBEMU_0x20;
                 },
                 // SET GBEMU_5, H
                 // #0xEC:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x2000;
                 },
                 // SET GBEMU_5, L
                 // #0xED:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x20;
                 },
                 // SET GBEMU_5, (HL)
                 // #0xEE:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) | GBEMU_0x20
                     );
                 },
                 // SET GBEMU_5, A
                 // #0xEF:
                 (parentObj) -> {
                     parentObj.registerA |= GBEMU_0x20;
                 },
                 // SET GBEMU_6, B
                 // #0xF0:
                 (parentObj) -> {
                     parentObj.registerB |= GBEMU_0x40;
                 },
                 // SET GBEMU_6, C
                 // #0xF1:
                 (parentObj) -> {
                     parentObj.registerC |= GBEMU_0x40;
                 },
                 // SET GBEMU_6, D
                 // #0xF2:
                 (parentObj) -> {
                     parentObj.registerD |= GBEMU_0x40;
                 },
                 // SET GBEMU_6, E
                 // #0xF3:
                 (parentObj) -> {
                     parentObj.registerE |= GBEMU_0x40;
                 },
                 // SET GBEMU_6, H
                 // #0xF4:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x4000;
                 },
                 // SET GBEMU_6, L
                 // #0xF5:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x40;
                 },
                 // SET GBEMU_6, (HL)
                 // #0xF6:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) | GBEMU_0x40
                     );
                 },
                 // SET GBEMU_6, A
                 // #0xF7:
                 (parentObj) -> {
                     parentObj.registerA |= GBEMU_0x40;
                 },
                 // SET GBEMU_7, B
                 // #0xF8:
                 (parentObj) -> {
                     parentObj.registerB |= GBEMU_0x80;
                 },
                 // SET GBEMU_7, C
                 // #0xF9:
                 (parentObj) -> {
                     parentObj.registerC |= GBEMU_0x80;
                 },
                 // SET GBEMU_7, D
                 // #0xFA:
                 (parentObj) -> {
                     parentObj.registerD |= GBEMU_0x80;
                 },
                 // SET GBEMU_7, E
                 // #0xFB:
                 (parentObj) -> {
                     parentObj.registerE |= GBEMU_0x80;
                 },
                 // SET GBEMU_7, H
                 // #0xFC:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x8000;
                 },
                 // SET GBEMU_7, L
                 // #0xFD:
                 (parentObj) -> {
                     parentObj.registersHL |= GBEMU_0x80;
                 },
                 // SET GBEMU_7, (HL)
                 // #0xFE:
                 (parentObj) -> {
                     parentObj.memoryWriter.get(parentObj.registersHL).call(
                             parentObj,
                             parentObj.registersHL,
                             parentObj.memoryReader.get(parentObj.registersHL).call(parentObj, parentObj.registersHL) | GBEMU_0x80
                     );
                 },
                 // SET GBEMU_7, A
                 // #0xFF:
                 (parentObj) -> {
                     parentObj.registerA |= GBEMU_0x80;
                 }
         };
 
         GameBoyCore(GameBoyCanvas canvas, String romImage) {
             this.canvas = canvas; // Canvas DOM object for drawing out the graphics to.
             this.romImage = romImage;
             this.updateGBBGPalette = GameBoyCore::updateGBColorizedBGPalette;
             this.updateGBOBJPalette = GameBoyCore::updateGBRegularOBJPalette;
             // Compile the LCD controller functions.
             this.initializeLCDController();
             this.initializeAudioStartState();
             this.initializeTiming();
             // Initialize the white noise cache tables ahead of time:
             this.intializeWhiteNoise();
         }
         public void returnFromRTCState() {
             debugLog("This is returnFromRTCState");
             if (this.openRTC != null && this.cTimeR) {
                 ArrayList<Object> rtcData = this.openRTC.call(this.name);
                 int index = 0;
                 this.lastIteration = (int) rtcData.get(index++);
                 this.rtcIsLatched = (boolean) rtcData.get(index++);
                 this.latchedSeconds = (int) rtcData.get(index++);
                 this.latchedMinutes = (int) rtcData.get(index++);
                 this.latchedHours = (int) rtcData.get(index++);
                 this.latchedLDays = (int) rtcData.get(index++);
                 this.latchedHDays = (int) rtcData.get(index++);
                 this.rtcSeconds = (int) rtcData.get(index++);
                 this.rtcMinutes = (int) rtcData.get(index++);
                 this.rtcHours = (int) rtcData.get(index++);
                 this.rtcDays = (int) rtcData.get(index++);
                 this.rtcDayOverFlow = (boolean) rtcData.get(index++);
                 this.rtcHalt = (boolean) rtcData.get(index);
             }
         }
         public void start() {
             debugLog("This is GameBoyCore-start");
             this.initMemory(); // Write the startup memory.
             this.romLoad(); // Load the rom into memory and get cartridge information from it.
             this.initLCD(); // Initialize the graphics.
             this.initSound(); // Sound object initialization.
             this.run(); // Start the emulation.
         }
         public void initMemory() {
             debugLog("This is initMemory");
             // Initialize the RAM:
             this.memory =  this.getTypedArray(GBEMU_0x10000, 0, "uint8");
             this.frameBuffer = this.getTypedArray(GBEMU_23040, GBEMU_0xF8F8F8, "int32");
             this.bgCHRBank1.array = this.getTypedArray(GBEMU_0x800, 0, "uint8");
             this.tickTable = this.toTypedArray(this.tickTable, "uint8");
             this.secondaryTickTable = this.toTypedArray(this.secondaryTickTable, "uint8");
             this.channel3PCM = this.getTypedArray(GBEMU_0x20, 0, "int8");
         }
         public ArrayList<ArrayObject> generateCacheArray(int tileAmount) {
             debugLog("This is generateCacheArray");
             ArrayList<ArrayObject> tileArray = new ArrayList<ArrayObject>();
             int tileNumber = 0;
             while (tileNumber < tileAmount) {
                 ArrayObject object = new ArrayObject();
                 object.array = this.getTypedArray(GBEMU_64, 0, "uint8");
                 tileArray.add(object);
                 tileNumber += 1;
             }
             return tileArray;
         }
         public void initSkipBootstrap() {
             debugLog("This is initSkipBootstrap");
             int index = GBEMU_0xFF;
             while (index >= 0) {
                 if (index >= GBEMU_0x30 && index < GBEMU_0x40) {
                     this.memoryWrite(GBEMU_0xFF00 | index, this.ffxxDump[index]);
                 } else {
                     switch (index) {
                         case GBEMU_0x00:
                         case GBEMU_0x01:
                         case GBEMU_0x02:
                         case GBEMU_0x05:
                         case GBEMU_0x07:
                         case GBEMU_0x0F:
                         case GBEMU_0xFF:
                             this.memoryWrite(GBEMU_0xFF00 | index, this.ffxxDump[index]);
                             break;
                         default:
                             this.memory.set(GBEMU_0xFF00 | index, this.ffxxDump[index]);
                     }
                 }
                 index -= 1;
             }
             if (this.cGBC) {
                 this.memory.set(GBEMU_0xFF6C, GBEMU_0xFE);
                 this.memory.set(GBEMU_0xFF74, GBEMU_0xFE);
             } else {
                 this.memory.set(GBEMU_0xFF48, GBEMU_0xFF);
                 this.memory.set(GBEMU_0xFF49, GBEMU_0xFF);
                 this.memory.set(GBEMU_0xFF6C, GBEMU_0xFF);
                 this.memory.set(GBEMU_0xFF74, GBEMU_0xFF);
             }
             cout("Starting without the GBC boot rom.", 0);
             this.registerA = this.cGBC ? GBEMU_0x11 : GBEMU_0x1;
             this.registerB = 0;
             this.registerC = GBEMU_0x13;
             this.registerD = 0;
             this.registerE = GBEMU_0xD8;
             this.fZero = true;
             this.fSubtract = false;
             this.fHalfCarry = true;
             this.fCarry = true;
             this.registersHL = GBEMU_0x014D;
             this.lcdControl = this.lineControl;
             this.ime = false;
             this.irqLineMatched = 0;
             this.interruptsRequested = GBEMU_225;
             this.interruptsEnabled = 0;
             this.hdmaRunning = false;
             this.cpuTicks = GBEMU_12;
             this.statTracker = 0;
             this.modeSTAT = 1;
             this.spriteCount = GBEMU_252;
             this.lycMatchTriggerSTAT = false;
             this.mode2TriggerSTAT = false;
             this.mode1TriggerSTAT = false;
             this.mode0TriggerSTAT = false;
             this.lcdIsOn = true;
             this.channel1FrequencyTracker = GBEMU_0x2000;
             this.channel1DutyTracker = 0;
             this.channel1CachedDuty = this.dutyLookup[GBEMU_2];
             this.channel1totalLength = 0;
             this.channel1envelopeVolume = GBEMU_0;
             this.channel1envelopeType = false;
             this.channel1envelopeSweeps = 0;
             this.channel1envelopeSweepsLast = GBEMU_0;
             this.channel1consecutive = true;
             this.channel1frequency = GBEMU_1985;
             this.channel1SweepFault = true;
             this.channel1ShadowFrequency = GBEMU_1985;
             this.channel1timeSweep = 1;
             this.channel1lastTimeSweep = 0;
             this.channel1numSweep = GBEMU_0;
             this.channel1frequencySweepDivider = 0;
             this.channel1decreaseSweep = false;
             this.channel2FrequencyTracker = GBEMU_0x2000;
             this.channel2DutyTracker = 0;
             this.channel2CachedDuty = this.dutyLookup[GBEMU_2];
             this.channel2totalLength = 0;
             this.channel2envelopeVolume = GBEMU_0;
             this.channel2envelopeType = false;
             this.channel2envelopeSweeps = 0;
             this.channel2envelopeSweepsLast = 0;
             this.channel2consecutive = true;
             this.channel2frequency = GBEMU_0;
             this.channel3canPlay = false;
             this.channel3totalLength = 0;
             this.channel3patternType = GBEMU_4;
             this.channel3frequency = 0;
             this.channel3consecutive = true;
             this.channel3Counter = GBEMU_0x418;
             this.channel4FrequencyPeriod = GBEMU_8;
             this.channel4totalLength = 0;
             this.channel4envelopeVolume = 0;
             this.channel4currentVolume = GBEMU_0;
             this.channel4envelopeType = false;
             this.channel4envelopeSweeps = 0;
             this.channel4envelopeSweepsLast = GBEMU_0;
             this.channel4consecutive = true;
             this.channel4BitRange = GBEMU_0x7FFF;
             this.channel4VolumeShifter = GBEMU_15;
             this.channel1FrequencyCounter = GBEMU_0x200;
             this.channel2FrequencyCounter = GBEMU_0x200;
             this.channel3Counter = GBEMU_0x800;
             this.channel3FrequencyPeriod = GBEMU_0x800;
             this.channel3lastSampleLookup = 0;
             this.channel4lastSampleLookup = GBEMU_0;
             this.vinLeftChannelMasterVolume = 1;
             this.vinRightChannelMasterVolume = 1;
             this.soundMasterEnabled = true;
             // left
             this.leftChannel1 = true;
             this.leftChannel2 = true;
             this.leftChannel3 = true;
             this.leftChannel4 = true;
             // right
             this.rightChannel1 = true;
             this.rightChannel2 = true;
             this.rightChannel3 = false;
             this.rightChannel4 = false;
             this.divTicks = GBEMU_27044;
             this.lcdTicks = GBEMU_160;
             this.timerTicks = 0;
             this.timaEnabled = false;
             this.tacClocker = GBEMU_1024;
             this.serialTimer = 0;
             this.serialShiftTimer = 0;
             this.serialShiftTimerAllocated = 0;
             this.irqEnableDelay = 0;
             this.actualScanLine = GBEMU_144;
             this.lastUnrenderedLine = GBEMU_0;
             this.gfxWindowDisplay = false;
             this.gfxSpriteShow = false;
             this.gfxSpriteNormalHeight = true;
             this.bgEnabled = true;
             this.bgPriorityEnabled = true;
             this.gfxWindowCHRBankPosition = GBEMU_0;
             this.gfxBackgroundCHRBankPosition = 0;
             this.gfxBackgroundBankOffset = 0;
             this.windowY = GBEMU_0;
             this.windowX = 0;
             this.drewBlank = GBEMU_0;
             this.midScanlineOffset = -1;
             this.currentX = GBEMU_0;
         }
         public void initBootstrap() {
             debugLog("This is initBootstrap");
             // Start as an unset device:
             cout("Starting the selected boot rom.", 0);
             this.programCounter = 0;
             this.stackPointer = 0;
             this.ime = false;
             this.lcdTicks = GBEMU_0;
             this.divTicks = 0;
             this.registerA = GBEMU_0;
             this.registerB = 0;
             this.registerC = GBEMU_0;
             this.registerD = 0;
             this.registerE = GBEMU_0;
             this.fZero = false;
             this.fSubtract = false;
             this.fHalfCarry = false;
             this.fCarry = false;
             this.registersHL = GBEMU_0;
             // left
             this.leftChannel1 = false;
             this.leftChannel2 = false;
             this.leftChannel3 = false;
             this.leftChannel4 = false;
             // right
             this.rightChannel1 = false;
             this.rightChannel2 = false;
             this.rightChannel3 = false;
             this.rightChannel4 = false;
             this.channel2frequency = GBEMU_0;
             this.channel1frequency = GBEMU_0;
             this.channel4consecutive = false;
             this.channel2consecutive = false;
             this.channel1consecutive = false;
             this.vinLeftChannelMasterVolume = GBEMU_8;
             this.vinRightChannelMasterVolume = GBEMU_8;
             this.memory.set(GBEMU_0xFF00, GBEMU_0xF); // Set the joypad state.
         }
         public void romLoad() {
             debugLog("This is romLoad");
             // Load the first two rom banks (0x0000 - 0x7FFF) into regular gameboy memory:
             this.rom = new ArrayList<Integer>();
             this.usedBootrom = (boolean) settings[1];
             int maxLength = this.romImage.length();
             if (maxLength < GBEMU_0x4000) {
                 return;
             }
             this.rom = this.getTypedArray(maxLength, 0, "uint8");
             int romIndex = 0;
             if (this.usedBootrom) {
                 if (!(boolean) settings[GBEMU_11]) {
                     // Patch in the GBC boot rom into the memory map:
                     while (romIndex < GBEMU_0x100) {
                         this.memory.set(romIndex, this.gbCBOOTrom[romIndex]); // Load in the GameBoy Color BOOT rom.
                         this.rom.set(romIndex, this.romImage.codePointAt(romIndex) & GBEMU_0xFF); // Decode the rom binary for the switch out.
                         romIndex += 1;
                     }
                     while (romIndex < GBEMU_0x200) {
                         this.rom.set(romIndex, this.romImage.codePointAt(romIndex) & GBEMU_0xFF); // Load in the game rom.
                         this.memory.set(romIndex, this.rom.get(romIndex));
                         romIndex += 1;
                     }
                     while (romIndex < GBEMU_0x900) {
                         this.memory.set(romIndex, this.gbCBOOTrom[romIndex - GBEMU_0x100]); // Load in the GameBoy Color BOOT rom.
                         this.rom.set(romIndex, this.romImage.codePointAt(romIndex) & GBEMU_0xFF); // Decode the rom binary for the switch out.
                         romIndex += 1;
                     }
                     this.usedGBCBootrom = true;
                 } else {
                     // Patch in the GBC boot rom into the memory map:
                     while (romIndex < GBEMU_0x100) {
                         this.memory.set(romIndex, this.gbBOOTrom[romIndex]); // Load in the GameBoy Color BOOT rom.
                         this.rom.set(romIndex, this.romImage.codePointAt(romIndex) & GBEMU_0xFF); // Decode the rom binary for the switch out.
                         romIndex += 1;
                     }
                 }
                 while (romIndex < GBEMU_0x4000) {
                     this.rom.set(romIndex, this.romImage.codePointAt(romIndex) & GBEMU_0xFF); // Load in the game rom.
                     this.memory.set(romIndex, this.rom.get(romIndex));
                     romIndex += 1;
                 }
             } else {
                 // Don't load in the boot rom:
                 while (romIndex < GBEMU_0x4000) {
                     this.rom.set(romIndex, this.romImage.codePointAt(romIndex) & GBEMU_0xFF); // Load in the game rom.
                     this.memory.set(romIndex, this.rom.get(romIndex));
                     romIndex += 1;
                 }
             }
             // Finish the decoding of the rom binary:
             while (romIndex < maxLength) {
                 this.rom.set(romIndex, this.romImage.codePointAt(romIndex) & GBEMU_0xFF);
                 romIndex += 1;
             }
             this.romBankEdge = (int) Math.floor((double) this.rom.size() / GBEMU_0x4000);
             // Set up the emulator for the cartidge specifics:
             this.interpretCartridge();
             // Check for IRQ matching upon initialization:
             this.checkIRQMatching();
         }
         public Object getromImage() {
             // Return the binary version of the rom image currently running:
             if (this.romImage.length() > 0) {
                 return this.romImage.length();
             }
             int length = this.rom.size();
             for (int index = 0; index < length; index++) {
                 this.romImage += String.valueOf(this.rom.get(index));
             }
             return this.romImage;
         }
         public void interpretCartridge() {
             debugLog("This is interpretCartridge");
             // rom name
             for (int index = GBEMU_0x134; index < GBEMU_0x13F; index++) {
                 if (((int) this.romImage.codePointAt(index)) > 0) {
                     this.name += String.valueOf(this.romImage.charAt(index));
                 }
             }
             // rom game code (for newer games)
             for (int index = GBEMU_0x13F; index < GBEMU_0x143; index++) {
                 if (this.romImage.codePointAt(index) > 0) {
                     this.gameCode += String.valueOf(this.romImage.charAt(index));
                 }
             }
             cout("Game Code: " + this.gameCode, 0);
             // Cartridge type
             this.cartridgeType = this.rom.get(GBEMU_0x147);
             cout("Cartridge type #" + this.cartridgeType, 0);
             // Map out rom cartridge sub-types.
             String mbcType = "";
             switch (this.cartridgeType) {
                 case GBEMU_0x00:
                     // rom w/o bank switching
                     if (!(boolean) settings[GBEMU_9]) {
                         mbcType = "rom";
                         break;
                     }
                 case GBEMU_0x01:
                     this.cMBC1 = true;
                     mbcType = "MBC1";
                     break;
                 case GBEMU_0x02:
                     this.cMBC1 = true;
                     this.cSRAM = true;
                     mbcType = "MBC1 + SRAM";
                     break;
                 case GBEMU_0x03:
                     this.cMBC1 = true;
                     this.cSRAM = true;
                     this.cBATT = true;
                     mbcType = "MBC1 + SRAM + BATT";
                     break;
                 case GBEMU_0x05:
                     this.cMBC2 = true;
                     mbcType = "MBC2";
                     break;
                 case GBEMU_0x06:
                     this.cMBC2 = true;
                     this.cBATT = true;
                     mbcType = "MBC2 + BATT";
                     break;
                 case GBEMU_0x08:
                     this.cSRAM = true;
                     mbcType = "rom + SRAM";
                     break;
                 case GBEMU_0x09:
                     this.cSRAM = true;
                     this.cBATT = true;
                     mbcType = "rom + SRAM + BATT";
                     break;
                 case GBEMU_0x0B:
                     this.cMMMO1 = true;
                     mbcType = "MMMO1";
                     break;
                 case GBEMU_0x0C:
                     this.cMMMO1 = true;
                     this.cSRAM = true;
                     mbcType = "MMMO1 + SRAM";
                     break;
                 case GBEMU_0x0D:
                     this.cMMMO1 = true;
                     this.cSRAM = true;
                     this.cBATT = true;
                     mbcType = "MMMO1 + SRAM + BATT";
                     break;
                 case GBEMU_0x0F:
                     this.cMBC3 = true;
                     this.cTimeR = true;
                     this.cBATT = true;
                     mbcType = "MBC3 + TimeR + BATT";
                     break;
                 case GBEMU_0x10:
                     this.cMBC3 = true;
                     this.cTimeR = true;
                     this.cBATT = true;
                     this.cSRAM = true;
                     mbcType = "MBC3 + TimeR + BATT + SRAM";
                     break;
                 case GBEMU_0x11:
                     this.cMBC3 = true;
                     mbcType = "MBC3";
                     break;
                 case GBEMU_0x12:
                     this.cMBC3 = true;
                     this.cSRAM = true;
                     mbcType = "MBC3 + SRAM";
                     break;
                 case GBEMU_0x13:
                     this.cMBC3 = true;
                     this.cSRAM = true;
                     this.cBATT = true;
                     mbcType = "MBC3 + SRAM + BATT";
                     break;
                 case GBEMU_0x19:
                     this.cMBC5 = true;
                     mbcType = "MBC5";
                     break;
                 case GBEMU_0x1A:
                     this.cMBC5 = true;
                     this.cSRAM = true;
                     mbcType = "MBC5 + SRAM";
                     break;
                 case GBEMU_0x1B:
                     this.cMBC5 = true;
                     this.cSRAM = true;
                     this.cBATT = true;
                     mbcType = "MBC5 + SRAM + BATT";
                     break;
                 case GBEMU_0x1C:
                     this.cRUMBLE = true;
                     mbcType = "RUMBLE";
                     break;
                 case GBEMU_0x1D:
                     this.cRUMBLE = true;
                     this.cSRAM = true;
                     mbcType = "RUMBLE + SRAM";
                     break;
                 case GBEMU_0x1E:
                     this.cRUMBLE = true;
                     this.cSRAM = true;
                     this.cBATT = true;
                     mbcType = "RUMBLE + SRAM + BATT";
                     break;
                 case GBEMU_0x1F:
                     this.cCamera = true;
                     mbcType = "GameBoy Camera";
                     break;
                 case GBEMU_0x22:
                     this.cMBC7 = true;
                     this.cSRAM = true;
                     this.cBATT = true;
                     mbcType = "MBC7 + SRAM + BATT";
                     break;
                 case GBEMU_0xFD:
                     this.cTAMA5 = true;
                     mbcType = "TAMA5";
                     break;
                 case GBEMU_0xFE:
                     this.cHuC3 = true;
                     mbcType = "HuC3";
                     break;
                 case GBEMU_0xFF:
                     this.cHuC1 = true;
                     mbcType = "HuC1";
                     break;
                 default:
                     mbcType = "Unknown";
                     cout("Cartridge type is unknown.", GBEMU_2);
                     pausePlay();
             }
             cout("Cartridge Type: " + mbcType + ".", 0);
             // rom and RAM banks
             this.numRomBanks = this.romBanks[this.rom.get(GBEMU_0x148)];
             cout(this.numRomBanks + " rom banks.", 0);
             switch (this.ramBanks[this.rom.get(GBEMU_0x149)]) {
                 case 0:
                     cout("No RAM banking requested for allocation or MBC is of type GBEMU_2.", 0);
                     break;
                 case GBEMU_2:
                     cout("1 RAM bank requested for allocation.", 0);
                     break;
                 case GBEMU_3:
                     cout("GBEMU_4 RAM banks requested for allocation.", 0);
                     break;
                 case GBEMU_4:
                     cout("GBEMU_16 RAM banks requested for allocation.", 0);
                     break;
                 default:
                     cout("RAM bank amount requested is unknown, will use maximum allowed by specified MBC type.", 0);
             }
             // Check the GB/GBC mode byte:
             if (!this.usedBootrom) {
                 switch (this.rom.get(GBEMU_0x143)) {
                     case GBEMU_0x00: // Only GB mode
                         this.cGBC = false;
                         cout("Only GB mode detected.", 0);
                         break;
                     case GBEMU_0x32: // Exception to the GBC identifying code:
                         if (!(boolean) settings[GBEMU_2] && this.name + this.gameCode + this.rom.get(GBEMU_0x143) == "Game and Watch GBEMU_50") {
                             this.cGBC = true;
                             cout("Created a boot exception for Game and Watch Gallery GBEMU_2 (GBC ID byte is wrong on the cartridge).", 1);
                         } else {
                             this.cGBC = false;
                         }
                         break;
                     case GBEMU_0x80: // Both GB + GBC modes
                         this.cGBC = !(boolean) settings[GBEMU_2];
                         cout("GB and GBC mode detected.", 0);
                         break;
                     case GBEMU_0xC0: // Only GBC mode
                         this.cGBC = true;
                         cout("Only GBC mode detected.", 0);
                         break;
                     default:
                         this.cGBC = false;
                         cout("Unknown GameBoy game type code #" + this.rom.get(GBEMU_0x143) + ", defaulting to GB mode (Old games dont have a type code).", 1);
                 }
                 this.inBootstrap = false;
                 // CPU/(V)RAM initialization.
                 this.setupRAM();
                 this.initSkipBootstrap();
                 // Line added for benchmarking.
                 this.initializeAudioStartState();
             } else {
                 // AAllow the GBC boot ROM to run in GBC mode...
                 this.cGBC = this.usedGBCBootrom;
                 // CPU/(V)RAM initialization.
                 this.setupRAM();
                 this.initBootstrap();
             }
             this.initializeModeSpecificArrays();
             int cOldLicense = this.rom.get(GBEMU_0x14B);
             int cNewLicense = (this.rom.get(GBEMU_0x144) & GBEMU_0xFF00) | (this.rom.get(GBEMU_0x145) & GBEMU_0xFF);
             if (cOldLicense != GBEMU_0x33) {
                 // Old Style License Header
                 cout("Old style license code: " + cOldLicense, 0);
             } else {
                 // New Style License Header
                 cout("New style license code: " + cNewLicense, 0);
             }
             this.romImage = ""; // Memory consumption reduction.
         }
         public void disableBootrom() {
             debugLog("This is disableBootrom");
             //Remove any traces of the boot rom from rom memory.
             for (int index = 0; index < GBEMU_0x100; ++index) {
                 this.memory.set(index, this.rom.get(index)); //Replace the GameBoy or GameBoy Color boot rom with the game rom.
             }
             if (this.usedGBCBootrom) {
                 //Remove any traces of the boot rom from rom memory.
                 for (int index = GBEMU_0x200; index < GBEMU_0x900; ++index) {
                     this.memory.set(index, this.rom.get(index)); //Replace the GameBoy Color boot rom with the game rom.
                 }
                 if (!this.cGBC) {
                     //Clean up the post-boot (GB mode only) state:
                     gBCtoGBModeAdjust();
                 } else {
                     recompileBootIOWriteHandling();
                 }
             } else {
                 recompileBootIOWriteHandling();
             }
         }
         public void initializeTiming() {
             debugLog("This is initializeTiming");
             //Emulator Timing:
             this.baseCPUCyclesPerIteration = ((double) GBEMU_0x80000 / (double) GBEMU_0x7D) * ((int) settings[GBEMU_6]);
             this.cpuCyclesTotalRoundoff = this.baseCPUCyclesPerIteration % GBEMU_4;
             this.cpuCyclesTotal = (int) (this.baseCPUCyclesPerIteration - this.cpuCyclesTotalRoundoff);
             this.cpuCyclesTotalBase = this.cpuCyclesTotal;
             this.cpuCyclesTotalCurrent = 0;
         }
         public void setupRAM() {
             debugLog("This is setupRAM");
             // Setup the auxilliary/switchable RAM:
             if (this.cMBC2) {
                 this.numRamBanks = 1 / GBEMU_16;
             } else if (this.cMBC1 || this.cRUMBLE || this.cMBC3 || this.cHuC3) {
                 this.numRamBanks = GBEMU_4;
             } else if (this.cMBC5) {
                 this.numRamBanks = GBEMU_16;
             } else if (this.cSRAM) {
                 this.numRamBanks = 1;
             }
             if (this.numRamBanks > 0) {
                 if (!this.mBCRAMUtilized()) {
                     // For rom and unknown MBC cartridges using the external RAM:
                     this.mbcRamBanksEnabled = true;
                 }
                 // Switched RAM Used
                 ArrayList<Integer> mbcRam = this.openMBC != null ? this.openMBC.call(this.name) : new ArrayList<>();
                 if (mbcRam.size() > 0) {
                     // Flash the SRAM into memory:
                     this.mbcRam = this.toIntegetTypedArray(mbcRam, "uint8");
                 } else {
                     this.mbcRam = this.getTypedArray(this.numRamBanks * GBEMU_0x2000, 0, "uint8");
                 }
             }
             cout("Actual bytes of MBC RAM allocated: " + this.numRamBanks * GBEMU_0x2000, 0);
             this.returnFromRTCState();
             // Setup the RAM for GBC mode.
             if (this.cGBC) {
                 this.vram = this.getTypedArray(GBEMU_0x2000, 0, "uint8");
                 this.gbcMemory = this.getTypedArray(GBEMU_0x7000, 0, "uint8");
             }
             this.memoryReadJumpCompile();
             this.memoryWriteJumpCompile();
         }
         public boolean mBCRAMUtilized() {
             debugLog("This is MBCRAMUtilized");
             return this.cMBC1 || this.cMBC2 || this.cMBC3 || this.cMBC5 || this.cMBC7 || this.cRUMBLE;
         }
         public void recomputeDimension() {
             debugLog("This is recomputeDimension");
             initNewCanvas();
             // Cache some dimension info:
             this.onscreenWidth = this.canvas.width;
             this.onscreenHeight = this.canvas.height;
             // The following line was modified for benchmarking:
             if (gameBoyWindow.mozRequestAnimationFrame) {
                 // Firefox slowness hack:
                 this.onscreenWidth = !(boolean) settings[GBEMU_12] ? GBEMU_160 : this.canvas.width;
                 this.canvas.width = this.onscreenWidth;
                 this.onscreenHeight = !(boolean) settings[GBEMU_12] ? GBEMU_144 : this.canvas.height;
                 this.canvas.height = this.onscreenHeight;
             } else {
                 this.onscreenWidth = this.canvas.width;
                 this.onscreenHeight = this.canvas.height;
             }
             this.offscreenWidth = !(boolean) settings[GBEMU_12] ? GBEMU_160 : this.canvas.width;
             this.offscreenHeight = !(boolean) settings[GBEMU_12] ? GBEMU_144 : this.canvas.height;
             this.offscreenRGBCount = this.offscreenWidth * this.offscreenHeight * GBEMU_4;
         }
         public void initLCD() {
             debugLog("This is initLCD");
             this.recomputeDimension();
             if (this.offscreenRGBCount != GBEMU_92160) {
                 // Only create the resizer handle if we need it:
                 this.compileResizeFrameBufferFunction();
             } else {
                 // Resizer not needed:
                 this.resizer = null;
             }
             this.canvasOffscreen = new GameBoyCanvas(); // Line modified for benchmarking.
             this.canvasOffscreen.width = this.offscreenWidth;
             this.canvasOffscreen.height = this.offscreenHeight;
             this.drawContextOffscreen = this.canvasOffscreen.getContext("2d");
             this.drawContextOnscreen = this.canvas.getContext("2d");
             // Get a CanvasPixelArray buffer:
             this.canvasBuffer = this.drawContextOffscreen.createImageData(this.offscreenWidth, this.offscreenHeight);
             int index = this.offscreenRGBCount;
             while (index > 0) {
                 index -= GBEMU_4;
                 this.canvasBuffer.data.set(index,  GBEMU_0xF8);
                 this.canvasBuffer.data.set(index + 1,  GBEMU_0xF8);
                 this.canvasBuffer.data.set(index + GBEMU_2,  GBEMU_0xF8);
                 this.canvasBuffer.data.set(index + GBEMU_3,  GBEMU_0xFF);
             }
             this.graphicsBlit();
             this.canvas.style.visibility = "visible";
             if (this.swizzledFrame == null || this.swizzledFrame.isEmpty()) {
                 this.swizzledFrame = this.<Integer>getTypedArray(GBEMU_69120, (Integer) GBEMU_0xFF, "uint8");
             }
             // Test the draw system and browser vblank latching:
             this.drewFrame = true; // Copy the latest graphics to buffer.
             this.requestDraw();
         }
         public void graphicsBlit() {
             debugLog("This is graphicsBlit");
             if (this.offscreenWidth == this.onscreenWidth && this.offscreenHeight == this.onscreenHeight) {
                 this.drawContextOnscreen.putImageData((GameBoyContextImageDataResult) this.canvasBuffer, 0, 0);
             } else {
                 this.drawContextOffscreen.putImageData((GameBoyContextImageDataResult) this.canvasBuffer, 0, 0);
                 this.drawContextOnscreen.drawImage((GameBoyCanvas) this.canvasOffscreen, 0, 0, this.onscreenWidth, this.onscreenHeight);
             }
         }
         public void joyPadEvent(int key, boolean down) {
             if (down) {
                 this.joyPad &= GBEMU_0xFF ^ (1 << key);
                 if (!this.cGBC && (!this.usedBootrom || !this.usedGBCBootrom)) {
                     this.interruptsRequested |= GBEMU_0x10; // A real GBC doesn't set this!
                     this.remainingClocks = 0;
                     this.checkIRQMatching();
                 }
             } else {
                 this.joyPad |= 1 << key;
             }
             this.memory.set(GBEMU_0xFF00,
                     (this.memory.get(GBEMU_0xFF00) & GBEMU_0x30) +
                             (((this.memory.get(GBEMU_0xFF00) & GBEMU_0x20) == 0 ? this.joyPad >> GBEMU_4 : GBEMU_0xF) &
                                     ((this.memory.get(GBEMU_0xFF00) & GBEMU_0x10) == 0 ? this.joyPad & GBEMU_0xF : GBEMU_0xF)));
             this.cpuStopped = false;
         }
         public void gyroEvent(int xTemp, int yTemp) {
             int x = xTemp;
             int y = yTemp;
             x *= -GBEMU_100;
             x += GBEMU_2047;
             this.highX = x >> GBEMU_8;
             this.lowX = x & GBEMU_0xFF;
             y *= -GBEMU_100;
             y += GBEMU_2047;
             this.highY = y >> GBEMU_8;
             this.lowY = y & GBEMU_0xFF;
         }
         public void initSound() {
             debugLog("This is initSound");
             this.sampleSize = ((double) GBEMU_0x400000 / (double) GBEMU_1000) * ((int) settings[GBEMU_6]);
             this.machineOut = (int) settings[GBEMU_13];
             if ((boolean) settings[0]) {
 
                 audioHandle = new XAudioServer(
                         GBEMU_2,
                         GBEMU_0x400000 / (int) settings[GBEMU_13],
                         0,
                         (int) Math.max((this.sampleSize * (int) settings[GBEMU_8]) / (int) settings[GBEMU_13], GBEMU_8192) << 1,
                         null,
                         (int) settings[GBEMU_14]
                 );
                 this.initAudioBuffer();
             } else if (this.audioHandle != null) {
                 // Mute the audio output, as it has an immediate silencing effect:
                 this.audioHandle.changeVolume(0);
             }
         }
         public void changeVolume() {
             if ((boolean) settings[0] && this.audioHandle != null) {
                 this.audioHandle.changeVolume((int) settings[GBEMU_14]);
             }
         }
         public void initAudioBuffer() {
             debugLog("This is initAudioBuffer");
             this.audioIndex = 0;
             this.bufferContainAmount = Math.max((int) (this.sampleSize * (int) settings[GBEMU_7]) / (int) settings[GBEMU_13], GBEMU_4096) << 1;
             this.numSamplesTotal = ((int) this.sampleSize - (((int) this.sampleSize) % (int) settings[GBEMU_13]));
             this.currentBuffer = this.getTypedArray(this.numSamplesTotal, GBEMU_0xF0F0, "int32");
             this.secondaryBuffer = this.getTypedArray((this.numSamplesTotal << 1) / (int) settings[GBEMU_13], 0, "float32");
         }
         public void intializeWhiteNoise() {
             debugLog("This is intializeWhiteNoise");
             // Noise Sample Tables:
             int randomFactor = 1;
             // GBEMU_15-bit lsfr Cache Generation:
             this.lsfr15Table = this.getTypedArray(GBEMU_0x80000, 0, "int8");
             int lsfr = GBEMU_0x7FFF; // Seed value has all its bits set.
             int lsfrShifted = GBEMU_0x3FFF;
             for (int index = 0; index < GBEMU_0x8000; ++index) {
                 // Normalize the last lsfr value for usage:
                 randomFactor = 1 - (lsfr & 1); // Docs say it's the inverse.
                 // Cache the different volume level results:
                 this.lsfr15Table.set(GBEMU_0x08000 | index, randomFactor);
                 this.lsfr15Table.set(GBEMU_0x10000 | index, randomFactor * GBEMU_0x2);
                 this.lsfr15Table.set(GBEMU_0x18000 | index, randomFactor * GBEMU_0x3);
                 this.lsfr15Table.set(GBEMU_0x20000 | index, randomFactor * GBEMU_0x4);
                 this.lsfr15Table.set(GBEMU_0x28000 | index, randomFactor * GBEMU_0x5);
                 this.lsfr15Table.set(GBEMU_0x30000 | index, randomFactor * GBEMU_0x6);
                 this.lsfr15Table.set(GBEMU_0x38000 | index, randomFactor * GBEMU_0x7);
                 this.lsfr15Table.set(GBEMU_0x40000 | index, randomFactor * GBEMU_0x8);
                 this.lsfr15Table.set(GBEMU_0x48000 | index, randomFactor * GBEMU_0x9);
                 this.lsfr15Table.set(GBEMU_0x50000 | index, randomFactor * GBEMU_0xA);
                 this.lsfr15Table.set(GBEMU_0x58000 | index, randomFactor * GBEMU_0xB);
                 this.lsfr15Table.set(GBEMU_0x60000 | index, randomFactor * GBEMU_0xC);
                 this.lsfr15Table.set(GBEMU_0x68000 | index, randomFactor * GBEMU_0xD);
                 this.lsfr15Table.set(GBEMU_0x70000 | index, randomFactor * GBEMU_0xE);
                 this.lsfr15Table.set(GBEMU_0x78000 | index, randomFactor * GBEMU_0xF);
                 // Recompute the lsfr algorithm:
                 lsfrShifted = lsfr >> 1;
                 lsfr = lsfrShifted | (((lsfrShifted ^ lsfr) & GBEMU_0x1) << GBEMU_14);
             }
             // GBEMU_7-bit lsfr Cache Generation:
             this.lsfr7Table = this.getTypedArray(GBEMU_0x800, 0, "int8");
             lsfr = GBEMU_0x7F; // Seed value has all its bits set.
             for (int index = 0; index < GBEMU_0x80; ++index) {
                 // Normalize the last lsfr value for usage:
                 randomFactor = 1 - (lsfr & 1); // Docs say it's the inverse.
                 // Cache the different volume level results:
                 this.lsfr7Table.set(GBEMU_0x080 | index, randomFactor);
                 this.lsfr7Table.set(GBEMU_0x100 | index, randomFactor * GBEMU_0x2);
                 this.lsfr7Table.set(GBEMU_0x180 | index, randomFactor * GBEMU_0x3);
                 this.lsfr7Table.set(GBEMU_0x200 | index, randomFactor * GBEMU_0x4);
                 this.lsfr7Table.set(GBEMU_0x280 | index, randomFactor * GBEMU_0x5);
                 this.lsfr7Table.set(GBEMU_0x300 | index, randomFactor * GBEMU_0x6);
                 this.lsfr7Table.set(GBEMU_0x380 | index, randomFactor * GBEMU_0x7);
                 this.lsfr7Table.set(GBEMU_0x400 | index, randomFactor * GBEMU_0x8);
                 this.lsfr7Table.set(GBEMU_0x480 | index, randomFactor * GBEMU_0x9);
                 this.lsfr7Table.set(GBEMU_0x500 | index, randomFactor * GBEMU_0xA);
                 this.lsfr7Table.set(GBEMU_0x580 | index, randomFactor * GBEMU_0xB);
                 this.lsfr7Table.set(GBEMU_0x600 | index, randomFactor * GBEMU_0xC);
                 this.lsfr7Table.set(GBEMU_0x680 | index, randomFactor * GBEMU_0xD);
                 this.lsfr7Table.set(GBEMU_0x700 | index, randomFactor * GBEMU_0xE);
                 this.lsfr7Table.set(GBEMU_0x780 | index, randomFactor * GBEMU_0xF);
                 // Recompute the lsfr algorithm:
                 lsfrShifted = lsfr >> 1;
                 lsfr = lsfrShifted | (((lsfrShifted ^ lsfr) & GBEMU_0x1) << GBEMU_6);
             }
             if (this.noiseSampleTable == null && this.memory.size() == GBEMU_0x10000) {
                 // If enabling audio for the first time after a game is already running, set up the internal table reference:
                 this.noiseSampleTable = (this.memory.get(GBEMU_0xFF22) & GBEMU_0x8) == GBEMU_0x8 ? this.lsfr7Table : this.lsfr15Table;
             }
         }
         public void audioUnderrunAdjustment() {
             debugLog("This is audioUnderrunAdjustment");
             if ((boolean) settings[0]) {
                 int underrunAmount = this.bufferContainAmount - this.audioHandle.remainingBuffer();
                 if (underrunAmount > 0) {
                     this.cpuCyclesTotalCurrent += (underrunAmount >> 1) * this.machineOut;
                     this.recalculateIterationClockLimit();
                 }
             }
         }
         public void initializeAudioStartState() {
             debugLog("This is initializeAudioStartState");
             this.channel1FrequencyTracker = GBEMU_0x2000;
             this.channel1DutyTracker = 0;
             this.channel1CachedDuty = this.dutyLookup[GBEMU_2];
             this.channel1totalLength = 0;
             this.channel1envelopeVolume = GBEMU_0;
             this.channel1envelopeType = false;
             this.channel1envelopeSweeps = GBEMU_0;
             this.channel1envelopeSweepsLast = GBEMU_0;
             this.channel1consecutive = true;
             this.channel1frequency = GBEMU_0;
             this.channel1SweepFault = false;
             this.channel1ShadowFrequency = GBEMU_0;
             this.channel1timeSweep = 1;
             this.channel1lastTimeSweep = GBEMU_0;
             this.channel1numSweep = GBEMU_0;
             this.channel1frequencySweepDivider = GBEMU_0;
             this.channel1decreaseSweep = false;
             this.channel2FrequencyTracker = GBEMU_0x2000;
             this.channel2DutyTracker = 0;
             this.channel2CachedDuty = this.dutyLookup[GBEMU_2];
             this.channel2totalLength = 0;
             this.channel2envelopeVolume = 0;
             this.channel2envelopeType = false;
             this.channel2envelopeSweeps = GBEMU_0;
             this.channel2envelopeSweepsLast = 0;
             this.channel2consecutive = true;
             this.channel2frequency = GBEMU_0;
             this.channel3canPlay = false;
             this.channel3totalLength = 0;
             this.channel3patternType = GBEMU_4;
             this.channel3frequency = 0;
             this.channel3consecutive = true;
             this.channel3Counter = GBEMU_0x800;
             this.channel4FrequencyPeriod = GBEMU_8;
             this.channel4totalLength = GBEMU_0;
             this.channel4envelopeVolume = GBEMU_0;
             this.channel4currentVolume = GBEMU_0;
             this.channel4envelopeType = false;
             this.channel4envelopeSweeps = 0;
             this.channel4envelopeSweepsLast = GBEMU_0;
             this.channel4consecutive = true;
             this.channel4BitRange = GBEMU_0x7FFF;
             this.noiseSampleTable = this.lsfr15Table;
             this.channel4VolumeShifter = GBEMU_15;
             this.channel1FrequencyCounter = GBEMU_0x2000;
             this.channel2FrequencyCounter = GBEMU_0x2000;
             this.channel3Counter = GBEMU_0x800;
             this.channel3FrequencyPeriod = GBEMU_0x800;
             this.channel3lastSampleLookup = GBEMU_0;
             this.channel4lastSampleLookup = 0;
             this.vinLeftChannelMasterVolume = GBEMU_8;
             this.vinRightChannelMasterVolume = GBEMU_8;
             this.mixerOutputCache = 0;
             this.sequencerClocks = GBEMU_0x2000;
             this.sequencePosition = 0;
             this.channel4FrequencyPeriod = GBEMU_8;
             this.channel4Counter = GBEMU_8;
             this.cachedChannel3Sample = 0;
             this.cachedChannel4Sample = 0;
             // default is false
             this.channel1Enabled = false;
             this.channel2Enabled = false;
             this.channel3Enabled = false;
             this.channel4Enabled = false;
             // default is false
             this.channel1canPlay = false;
             this.channel2canPlay = false;
             this.channel4canPlay = false;
             // cahce
             this.channel1OutputLevelCache();
             this.channel2OutputLevelCache();
             this.channel3OutputLevelCache();
             this.channel4OutputLevelCache();
         }
         public void outputAudio() {
             debugLog("This is outputAudio");
             int sampleFactor = 0;
             int dirtySample = 0;
             int averageL = 0;
             int averageR = 0;
             int destinationPosition = 0;
             int divisor1 = (int) settings[GBEMU_13];
             int divisor2 = divisor1 * GBEMU_0xF0;
             int sourcePosition = 0;
             while (sourcePosition < this.numSamplesTotal) {
                 sampleFactor = 0;
                 averageL = 0;
                 averageR = 0;
                 while (sampleFactor < divisor1) {
                     dirtySample = this.currentBuffer.get(sourcePosition++);
                     averageL += dirtySample >> GBEMU_9;
                     averageR += dirtySample & GBEMU_0x1FF;
                     sampleFactor += 1;
                 }
                 this.secondaryBuffer.set(destinationPosition++, averageL / divisor2 - 1);
                 this.secondaryBuffer.set(destinationPosition++, averageR / divisor2 - 1);
             }
             this.audioHandle.writeAudioNoCallback(this.secondaryBuffer);
         }
         // Below are the audio generation functions timed against the CPU:
         public void generateAudio(int numSamplesTemp) {
             debugLog("This is generateAudio");
             int numSamples = numSamplesTemp;
             if (this.soundMasterEnabled && !this.cpuStopped) {
                 int samplesToGenerate = 0;
                 while (numSamples > 0) {
                     samplesToGenerate = numSamples < this.sequencerClocks ? numSamples : this.sequencerClocks;
                     this.sequencerClocks -= samplesToGenerate;
                     numSamples -= samplesToGenerate;
                     samplesToGenerate -= 1;
                     while (samplesToGenerate > -1) {
                         this.computeAudioChannels();
                         this.currentBuffer.set(this.audioIndex++, this.mixerOutputCache);
                         if (this.audioIndex == this.numSamplesTotal) {
                             this.audioIndex = 0;
                             this.outputAudio();
                         }
                         samplesToGenerate -= 1;
                     }
                     if (this.sequencerClocks == 0) {
                         this.audioComputeSequencer();
                         this.sequencerClocks = GBEMU_0x2000;
                     }
                 }
             } else {
                 // SILENT OUTPUT:
                 numSamples -= 1;
                 while (numSamples > -1) {
                     numSamples -= 1;
                     this.currentBuffer.set(this.audioIndex++, GBEMU_0xF0F0);
                     if (this.audioIndex == this.numSamplesTotal) {
                         this.audioIndex = 0;
                         this.outputAudio();
                     }
                 }
             }
         }
         // Generate audio, but don't actually output it (Used for when sound is disabled by user/browser):
         public void generateAudioFake(int numSamplesTemp) {
             debugLog("This is generateAudioFake");
             if (this.soundMasterEnabled && !this.cpuStopped) {
                 int numSamples = numSamplesTemp - 1;
                 while (numSamples > -1) {
                     this.computeAudioChannels();
                     this.sequencerClocks -= 1;
                     if (this.sequencerClocks == 0) {
                         this.audioComputeSequencer();
                         this.sequencerClocks = GBEMU_0x2000;
                     }
                     numSamples -= 1;
                 }
             }
         }
         public void audioJIT() {
             debugLog("This is audioJIT");
             // Audio Sample Generation Timing:
             if ((boolean) settings[GBEMU_0]) {
                 this.generateAudio((int) this.audioTicks);
             } else {
                 this.generateAudioFake((int) this.audioTicks);
             }
             this.audioTicks = GBEMU_0;
         }
         public void audioComputeSequencer() {
             debugLog("This is audioComputeSequencer");
             switch (this.sequencePosition++) {
                 case 0:
                     this.clockAudioLength();
                     break;
                 case GBEMU_2:
                     this.clockAudioLength();
                     this.clockAudioSweep();
                     break;
                 case GBEMU_4:
                     this.clockAudioLength();
                     break;
                 case GBEMU_6:
                     this.clockAudioLength();
                     this.clockAudioSweep();
                     break;
                 case GBEMU_7:
                     this.clockAudioEnvelope();
                     this.sequencePosition = 0;
                 default:
                     break;
             }
         }
         public void clockAudioLength() {
             // Channel 1:
             if (this.channel1totalLength > 1) {
                 this.channel1totalLength -= 1;
             } else if (this.channel1totalLength == 1) {
                 this.channel1totalLength = 0;
                 this.channel1EnableCheck();
                 this.memory.set(GBEMU_0xFF26, this.memory.get(GBEMU_0xFF26) & GBEMU_0xFE); // Channel #1 On Flag Off
             }
             // Channel GBEMU_2:
             if (this.channel2totalLength > 1) {
                 this.channel2totalLength -= 1;
             } else if (this.channel2totalLength == 1) {
                 this.channel2totalLength = 0;
                 this.channel2EnableCheck();
                 this.memory.set(GBEMU_0xFF26, this.memory.get(GBEMU_0xFF26) & GBEMU_0xFD); // Channel #GBEMU_2 On Flag Off
             }
             // Channel GBEMU_3:
             if (this.channel3totalLength > 1) {
                 this.channel3totalLength -= 1;
             } else if (this.channel3totalLength == 1) {
                 this.channel3totalLength = 0;
                 this.channel3EnableCheck();
                 this.memory.set(GBEMU_0xFF26, this.memory.get(GBEMU_0xFF26) & GBEMU_0xFB); // Channel #GBEMU_3 On Flag Off
             }
             // Channel GBEMU_4:
             if (this.channel4totalLength > 1) {
                 this.channel4totalLength -= 1;
             } else if (this.channel4totalLength == 1) {
                 this.channel4totalLength = 0;
                 this.channel4EnableCheck();
                 this.memory.set(GBEMU_0xFF26, this.memory.get(GBEMU_0xFF26) & GBEMU_0xF7); // Channel #GBEMU_4 On Flag Off
             }
         }
         public void clockAudioSweep() {
             // Channel 1:
             if (!this.channel1SweepFault && this.channel1timeSweep > 0) {
                 this.channel1timeSweep -= 1;
                 if (this.channel1timeSweep == 0) {
                     this.runAudioSweep();
                 }
             }
         }
         public void runAudioSweep() {
             debugLog("This is runAudioSweep");
             // Channel 1:
             if (this.channel1lastTimeSweep > 0) {
                 if (this.channel1frequencySweepDivider > 0) {
                     if (this.channel1numSweep > 0) {
                         this.channel1numSweep -= 1;
                         if (this.channel1decreaseSweep) {
                             this.channel1ShadowFrequency -= this.channel1ShadowFrequency >> this.channel1frequencySweepDivider;
                             this.channel1frequency = this.channel1ShadowFrequency & GBEMU_0x7FF;
                             this.channel1FrequencyTracker = (GBEMU_0x800 - this.channel1frequency) << GBEMU_2;
                         } else {
                             this.channel1ShadowFrequency += this.channel1ShadowFrequency >> this.channel1frequencySweepDivider;
                             this.channel1frequency = this.channel1ShadowFrequency;
                             if (this.channel1ShadowFrequency <= GBEMU_0x7FF) {
                                 this.channel1FrequencyTracker = (GBEMU_0x800 - this.channel1frequency) << GBEMU_2;
                                 // Run overflow check twice:
                                 if (this.channel1ShadowFrequency + (this.channel1ShadowFrequency >> this.channel1frequencySweepDivider) > GBEMU_0x7ff) {
                                     this.channel1SweepFault = true;
                                     this.channel1EnableCheck();
                                     this.memory.set(GBEMU_0xFF26, this.memory.get(GBEMU_0xFF26) & GBEMU_0xFE); // Channel #1 On Flag Off
                                 }
                             } else {
                                 this.channel1frequency &= GBEMU_0x7FF;
                                 this.channel1SweepFault = true;
                                 this.channel1EnableCheck();
                                 this.memory.set(GBEMU_0xFF26, this.memory.get(GBEMU_0xFF26) & GBEMU_0xFE); // Channel #1 On Flag Off
                             }
                         }
                     }
                     this.channel1timeSweep = this.channel1lastTimeSweep;
                 } else {
                     // Channel has sweep disabled and timer becomes a length counter:
                     this.channel1SweepFault = true;
                     this.channel1EnableCheck();
                 }
             }
         }
         public void clockAudioEnvelope() {
             debugLog("This is clockAudioEnvelope");
             // Channel 1:
             if (this.channel1envelopeSweepsLast > -1) {
                 if (this.channel1envelopeSweeps > 0) {
                     this.channel1envelopeSweeps -= 1;
                 } else {
                     if (!this.channel1envelopeType) {
                         if (this.channel1envelopeVolume > 0) {
                             this.channel1envelopeVolume -= 1;
                             this.channel1envelopeSweeps = this.channel1envelopeSweepsLast;
                             this.channel1OutputLevelCache();
                         } else {
                             this.channel1envelopeSweepsLast = -1;
                         }
                     } else if (this.channel1envelopeVolume < GBEMU_0xF) {
                         this.channel1envelopeVolume += 1;
                         this.channel1envelopeSweeps = this.channel1envelopeSweepsLast;
                         this.channel1OutputLevelCache();
                     } else {
                         this.channel1envelopeSweepsLast = -1;
                     }
                 }
             }
             // Channel GBEMU_2:
             if (this.channel2envelopeSweepsLast > -1) {
                 if (this.channel2envelopeSweeps > 0) {
                     this.channel2envelopeSweeps -= 1;
                 } else {
                     if (!this.channel2envelopeType) {
                         if (this.channel2envelopeVolume > 0) {
                             this.channel2envelopeVolume -= 1;
                             this.channel2envelopeSweeps = this.channel2envelopeSweepsLast;
                             this.channel2OutputLevelCache();
                         } else {
                             this.channel2envelopeSweepsLast = -1;
                         }
                     } else if (this.channel2envelopeVolume < GBEMU_0xf) {
                         this.channel2envelopeVolume += 1;
                         this.channel2envelopeSweeps = this.channel2envelopeSweepsLast;
                         this.channel2OutputLevelCache();
                     } else {
                         this.channel2envelopeSweepsLast = -1;
                     }
                 }
             }
             // Channel GBEMU_4:
             if (this.channel4envelopeSweepsLast > -1) {
                 if (this.channel4envelopeSweeps > 0) {
                     this.channel4envelopeSweeps -= 1;
                 } else {
                     if (!this.channel4envelopeType) {
                         if (this.channel4envelopeVolume > 0) {
                             this.channel4envelopeVolume -= 1;
                             this.channel4currentVolume = this.channel4envelopeVolume << this.channel4VolumeShifter;
                             this.channel4envelopeSweeps = this.channel4envelopeSweepsLast;
                             this.channel4UpdateCache();
                         } else {
                             this.channel4envelopeSweepsLast = -1;
                         }
                     } else if (this.channel4envelopeVolume < GBEMU_0xF) {
                         this.channel4envelopeVolume += 1;
                         this.channel4currentVolume = this.channel4envelopeVolume << this.channel4VolumeShifter;
                         this.channel4envelopeSweeps = this.channel4envelopeSweepsLast;
                         this.channel4UpdateCache();
                     } else {
                         this.channel4envelopeSweepsLast = -1;
                     }
                 }
             }
         }
         public void computeAudioChannels() {
             // Channel 1 counter:
             this.channel1FrequencyCounter -= 1;
             if (this.channel1FrequencyCounter == 0) {
                 this.channel1FrequencyCounter = this.channel1FrequencyTracker;
                 this.channel1DutyTracker = (this.channel1DutyTracker + 1) & GBEMU_0x7;
                 this.channel1OutputLevelTrimaryCache();
             }
             // Channel GBEMU_2 counter:
             this.channel2FrequencyCounter -= 1;
             if (this.channel2FrequencyCounter == 0) {
                 this.channel2FrequencyCounter = this.channel2FrequencyTracker;
                 this.channel2DutyTracker = (this.channel2DutyTracker + 1) & GBEMU_0x7;
                 this.channel2OutputLevelTrimaryCache();
             }
             // Channel GBEMU_3 counter:
             this.channel3Counter -= 1;
             if (this.channel3Counter == 0) {
                 if (this.channel3canPlay) {
                     this.channel3lastSampleLookup = (this.channel3lastSampleLookup + 1) & GBEMU_0x1f;
                 }
                 this.channel3Counter = this.channel3FrequencyPeriod;
                 this.channel3UpdateCache();
             }
             // Channel GBEMU_4 counter:
             this.channel4Counter -= 1;
             if (this.channel4Counter == 0) {
                 this.channel4lastSampleLookup = (this.channel4lastSampleLookup + 1) & this.channel4BitRange;
                 this.channel4Counter = this.channel4FrequencyPeriod;
                 this.channel4UpdateCache();
             }
         }
         public void channel1EnableCheck() {
             this.channel1Enabled = (this.channel1consecutive || this.channel1totalLength > 0) && !this.channel1SweepFault && this.channel1canPlay;
             this.channel1OutputLevelSecondaryCache();
         }
         public void channel1VolumeEnableCheck() {
             this.channel1canPlay = this.memory.get(GBEMU_0xFF12) > GBEMU_7;
             this.channel1EnableCheck();
             this.channel1OutputLevelSecondaryCache();
         }
         public void channel1OutputLevelCache() {
             debugLog("This is channel1OutputLevelCache");
             this.channel1currentSampleLeft = this.leftChannel1 ? this.channel1envelopeVolume : 0;
             this.channel1currentSampleRight = this.rightChannel1 ? this.channel1envelopeVolume : 0;
             this.channel1OutputLevelSecondaryCache();
         }
         public void channel1OutputLevelSecondaryCache() {
             debugLog("This is channel1OutputLevelSecondaryCache");
             if (this.channel1Enabled) {
                 // is true
                 this.channel1currentSampleLeftSecondary = this.channel1currentSampleLeft;
                 this.channel1currentSampleRightSecondary = this.channel1currentSampleRight;
             } else {
                 // is false
                 this.channel1currentSampleLeftSecondary = 0;
                 this.channel1currentSampleRightSecondary = 0;
             }
             this.channel1OutputLevelTrimaryCache();
         }
         public void channel1OutputLevelTrimaryCache() {
             debugLog("This is channel1OutputLevelTrimaryCache");
             if (this.channel1CachedDuty[this.channel1DutyTracker]) {
                 // is true
                 this.channel1currentSampleLeftTrimary = this.channel1currentSampleLeftSecondary;
                 this.channel1currentSampleRightTrimary = this.channel1currentSampleRightSecondary;
             } else {
                 // is false
                 this.channel1currentSampleLeftTrimary = 0;
                 this.channel1currentSampleRightTrimary = 0;
             }
             this.mixerOutputLevelCache();
         }
         public void channel2EnableCheck() {
             this.channel2Enabled = (this.channel2consecutive || this.channel2totalLength > 0) && this.channel2canPlay;
             this.channel2OutputLevelSecondaryCache();
         }
         public void channel2VolumeEnableCheck() {
             this.channel2canPlay = this.memory.get(GBEMU_0xFF17) > GBEMU_7;
             this.channel2EnableCheck();
             this.channel2OutputLevelSecondaryCache();
         }
         public void channel2OutputLevelCache() {
             debugLog("This is channel2OutputLevelCache");
             this.channel2currentSampleLeft = this.leftChannel2 ? this.channel2envelopeVolume : 0;
             this.channel2currentSampleRight = this.rightChannel2 ? this.channel2envelopeVolume : 0;
             this.channel2OutputLevelSecondaryCache();
         }
         public void channel2OutputLevelSecondaryCache() {
             debugLog("This is channel2OutputLevelSecondaryCache");
             if (this.channel2Enabled) {
                 // is true
                 this.channel2currentSampleLeftSecondary = this.channel2currentSampleLeft;
                 this.channel2currentSampleRightSecondary = this.channel2currentSampleRight;
             } else {
                 // is false
                 this.channel2currentSampleLeftSecondary = 0;
                 this.channel2currentSampleRightSecondary = 0;
             }
             this.channel2OutputLevelTrimaryCache();
         }
         public void channel2OutputLevelTrimaryCache() {
             debugLog("This is channel2OutputLevelTrimaryCache");
             if (this.channel2CachedDuty[this.channel2DutyTracker]) {
                 // is true
                 this.channel2currentSampleLeftTrimary = this.channel2currentSampleLeftSecondary;
                 this.channel2currentSampleRightTrimary = this.channel2currentSampleRightSecondary;
             } else {
                 // is false
                 this.channel2currentSampleLeftTrimary = 0;
                 this.channel2currentSampleRightTrimary = 0;
             }
             this.mixerOutputLevelCache();
         }
         public void channel3EnableCheck() {
             this.channel3Enabled = /* this.channel3canPlay && */ this.channel3consecutive || this.channel3totalLength > 0;
             this.channel3OutputLevelSecondaryCache();
         }
         public void channel3OutputLevelCache() {
             this.channel3currentSampleLeft = this.leftChannel3 ? this.cachedChannel3Sample : 0;
             this.channel3currentSampleRight = this.rightChannel3 ? this.cachedChannel3Sample : 0;
             this.channel3OutputLevelSecondaryCache();
         }
         public void channel3OutputLevelSecondaryCache() {
             if (this.channel3Enabled) {
                 // is true
                 this.channel3currentSampleLeftSecondary = this.channel3currentSampleLeft;
                 this.channel3currentSampleRightSecondary = this.channel3currentSampleRight;
             } else {
                 // is false
                 this.channel3currentSampleLeftSecondary = 0;
                 this.channel3currentSampleRightSecondary = 0;
             }
             this.mixerOutputLevelCache();
         }
         public void channel4EnableCheck() {
             this.channel4Enabled = (this.channel4consecutive || this.channel4totalLength > 0) && this.channel4canPlay;
             this.channel4OutputLevelSecondaryCache();
         }
         public void channel4VolumeEnableCheck() {
             this.channel4canPlay = this.memory.get(GBEMU_0xFF21) > GBEMU_7;
             this.channel4EnableCheck();
             this.channel4OutputLevelSecondaryCache();
         }
         public void channel4OutputLevelCache() {
             this.channel4currentSampleLeft = this.leftChannel4 ? this.cachedChannel4Sample : 0;
             this.channel4currentSampleRight = this.rightChannel4 ? this.cachedChannel4Sample : 0;
             this.channel4OutputLevelSecondaryCache();
         }
         public void channel4OutputLevelSecondaryCache() {
             if (this.channel4Enabled) {
                 // is true
                 this.channel4currentSampleLeftSecondary = this.channel4currentSampleLeft;
                 this.channel4currentSampleRightSecondary = this.channel4currentSampleRight;
             } else {
                 // is false
                 this.channel4currentSampleLeftSecondary = 0;
                 this.channel4currentSampleRightSecondary = 0;
             }
             this.mixerOutputLevelCache();
         }
         public void mixerOutputLevelCache() {
             this.mixerOutputCache =
                     (((this.channel1currentSampleLeftTrimary +
                             this.channel2currentSampleLeftTrimary +
                             this.channel3currentSampleLeftSecondary +
                             this.channel4currentSampleLeftSecondary) *
                             this.vinLeftChannelMasterVolume) <<
                             GBEMU_9) +
                             (this.channel1currentSampleRightTrimary +
                                     this.channel2currentSampleRightTrimary +
                                     this.channel3currentSampleRightSecondary +
                                     this.channel4currentSampleRightSecondary) *
                                     this.vinRightChannelMasterVolume;
         }
         public void channel3UpdateCache() {
             this.cachedChannel3Sample = this.channel3PCM.get(this.channel3lastSampleLookup) >> this.channel3patternType;
             this.channel3OutputLevelCache();
         }
         public void channel3WriteRAM(int addressTemp, int data) {
             int address = addressTemp;
             if (this.channel3canPlay) {
                 this.audioJIT();
                 // address = this.channel3lastSampleLookup >> 1;
             }
             this.memory.set(GBEMU_0xFF30 | address, data);
             address <<= 1;
             this.channel3PCM.set(address, (data >> GBEMU_4));
             this.channel3PCM.set((address | 1), (data & GBEMU_0xF));
         }
         public void channel4UpdateCache() {
             this.cachedChannel4Sample = this.noiseSampleTable.get(this.channel4currentVolume | this.channel4lastSampleLookup);
             this.channel4OutputLevelCache();
         }
         public void run() {
             debugLog("This is GameBoyCore run");
             // The preprocessing before the actual iteration loop:
             if ((this.stopEmulator & GBEMU_2) == 0) {
                 if ((this.stopEmulator & GBEMU_1) == 1) {
                     if (!this.cpuStopped) {
                         this.stopEmulator = GBEMU_0;
                         this.drewFrame = false;
                         this.audioUnderrunAdjustment();
                         // RTC clocking.
                         this.clockUpdate();
                         if (!this.halt) {
                             this.executeIteration();
                         } else {
                             // Finish the HALT rundown execution.
                             this.cpuTicks = GBEMU_0;
                             this.calculateHALTPeriod();
                             if (this.halt) {
                                 this.updateCoreFull(); // true
                             } else {
                                 this.executeIteration();
                             }
                         }
                         this.requestDraw(); // Request the graphics target to be updated
                     } else {
                         this.audioUnderrunAdjustment();
                         this.audioTicks += this.cpuCyclesTotal;
                         this.audioJIT();
                         this.stopEmulator |= GBEMU_1; // End current loop.
                     }
                 } else {
                     // We can only get here if there was an internal error, but the loop was restarted.
                     cout("Iterator restarted a faulted core.", GBEMU_2);
                     pausePlay();
                 }
             }
         }
         public void executeIteration() {
             debugLog("This is executeIteration");
             // Iterate the interpreter loop:
             int opcodeToExecute = 0;
             int timedTicks = 0;
             while (this.stopEmulator == 0) {
                 // Interrupt Arming:
                 switch (this.irqEnableDelay) {
                     case GBEMU_1:
                         this.ime = true;
                         this.checkIRQMatching();
                     case GBEMU_2:
                         this.irqEnableDelay -= 1;
                     default:
                         break;
                 }
                 // Is an IRQ set to fire?:
                 if (this.irqLineMatched > GBEMU_0) {
                     // ime is true and and interrupt was matched:
                     this.launchIRQ();
                 }
                 opcodeToExecute = this.memoryReader.get(this.programCounter).call(this, this.programCounter); // Fetch the current opcode
                 // Increment the program counter to the next instruction:
                 this.programCounter = (this.programCounter + 1) & GBEMU_0xFFFF;
                 // Check for the program counter quirk:
                 if (this.skipPCIncrement) {
                     this.programCounter = (this.programCounter - 1) & GBEMU_0xFFFF;
                     this.skipPCIncrement = false;
                 }
                 // Get how many CPU cycles the current instruction counts for:
                 this.cpuTicks = this.tickTable[opcodeToExecute];
                 // Execute the current instruction:
                 this.opCode[opcodeToExecute].call(this);
                 // Update the clocking for the LCD emulation:
                 // Update the state (Inlined updateCoreFull manually here):
                 this.lcdTicks += this.cpuTicks >> this.doubleSpeedShifter;
                 // Scan Line and STAT Mode Control
                 this.lcdControl[this.actualScanLine].call(this);
                 // Single-speed relative timing for A/V emulation:
                 timedTicks = this.cpuTicks >> this.doubleSpeedShifter;
                 // Audio Timing
                 this.audioTicks += timedTicks;
                 // Emulator Timing
                 this.emulatorTicks += timedTicks;
                 // CPU Timers:
                 this.divTicks += this.cpuTicks;
                 if (this.timaEnabled) {
                     // TIMA Timing
                     this.timerTicks += this.cpuTicks;
                     while (this.timerTicks >= this.tacClocker) {
                         this.timerTicks -= this.tacClocker;
                         this.memory.set(GBEMU_0xFF05, (this.memory.get(GBEMU_0xFF05) + GBEMU_1));
                         if (this.memory.get(GBEMU_0xFF05) == GBEMU_0x100) {
                             this.memory.set(GBEMU_0xFF05, this.memory.get(GBEMU_0xFF06));
                             this.interruptsRequested |= GBEMU_0x4;
                             this.checkIRQMatching();
                         }
                     }
                 }
                 if (this.serialTimer > GBEMU_0) {
                     // Serial Timing
                     // IRQ Counter:
                     this.serialTimer -= this.cpuTicks;
                     if (this.serialTimer <= GBEMU_0) {
                         this.interruptsRequested |= GBEMU_0x8;
                         this.checkIRQMatching();
                     }
                     // Bit Shit Counter:
                     this.serialShiftTimer -= this.cpuTicks;
                     if (this.serialShiftTimer <= GBEMU_0) {
                         this.serialShiftTimer = this.serialShiftTimerAllocated;
                         this.memory.set(GBEMU_0xFF01, ((this.memory.get(GBEMU_0xFF01) << GBEMU_1) & GBEMU_0xFE) | GBEMU_0x01);// We could shift in actual link data here if we were to implement such!!!
                     }
                 }
                 // End of iteration routine:
                 if (this.emulatorTicks >= this.cpuCyclesTotal) {
                     this.iterationEndRoutine();
                 }
                 // Start of code added for benchmarking:
                 this.instructions += 1;
                 if (this.instructions > this.totalInstructions) {
                     this.iterationEndRoutine();
                     this.stopEmulator |= GBEMU_2;
                     checkFinalState();
                 }
                 // End of code added for benchmarking.
             }
         }
         public void iterationEndRoutine() {
             debugLog("This is iterationEndRoutine");
             if ((this.stopEmulator & GBEMU_0x1) == 0) {
                 this.audioJIT(); // Make sure we at least output once per iteration.
                 // Update DIV Alignment (Integer overflow safety):
                 this.memory.set(GBEMU_0xFF04, (this.memory.get(GBEMU_0xFF04) + (this.divTicks >> GBEMU_8)) & GBEMU_0xFF);
                 this.divTicks &= GBEMU_0xFF;
                 // Update emulator flags:
                 this.stopEmulator |= 1; // End current loop.
                 this.emulatorTicks -= this.cpuCyclesTotal;
                 this.cpuCyclesTotalCurrent += this.cpuCyclesTotalRoundoff;
                 this.recalculateIterationClockLimit();
             }
         }
         public void handleSTOP() {
             debugLog("This is handleSTOP");
             this.cpuStopped = true; // Stop CPU until joypad input changes.
             this.iterationEndRoutine();
             if (this.emulatorTicks < 0) {
                 this.audioTicks -= this.emulatorTicks;
                 this.audioJIT();
             }
         }
         public void recalculateIterationClockLimit() {
             debugLog("This is recalculateIterationClockLimit");
             int endModulus = this.cpuCyclesTotalCurrent % GBEMU_4;
             this.cpuCyclesTotal = this.cpuCyclesTotalBase + this.cpuCyclesTotalCurrent - endModulus;
             this.cpuCyclesTotalCurrent = endModulus;
         }
         public void scanLineMode2() {
             // OAM Search Period
             if (this.statTracker != 1) {
                 if (this.mode2TriggerSTAT) {
                     this.interruptsRequested |= GBEMU_0x2;
                     this.checkIRQMatching();
                 }
                 this.statTracker = 1;
                 this.modeSTAT = GBEMU_2;
             }
         }
         public void scanLineMode3() {
             // Scan Line Drawing Period
             if (this.modeSTAT != GBEMU_3) {
                 if (this.statTracker == 0 && this.mode2TriggerSTAT) {
                     this.interruptsRequested |= GBEMU_0x2;
                     this.checkIRQMatching();
                 }
                 this.statTracker = 1;
                 this.modeSTAT = GBEMU_3;
             }
         }
         public void scanLineMode0() {
             // Horizontal Blanking Period
             if (this.modeSTAT != 0) {
                 if (this.statTracker != GBEMU_2) {
                     if (this.statTracker == 0) {
                         if (this.mode2TriggerSTAT) {
                             this.interruptsRequested |= GBEMU_0x2;
                             this.checkIRQMatching();
                         }
                         this.modeSTAT = GBEMU_3;
                     }
                     this.incrementScanLineQueue();
                     this.updateSpriteCount(this.actualScanLine);
                     this.statTracker = GBEMU_2;
                 }
                 if (this.lcdTicks >= this.spriteCount) {
                     if (this.hdmaRunning) {
                         this.executeHDMA();
                     }
                     if (this.mode0TriggerSTAT) {
                         this.interruptsRequested |= GBEMU_0x2;
                         this.checkIRQMatching();
                     }
                     this.statTracker = GBEMU_3;
                     this.modeSTAT = 0;
                 }
             }
         }
         public int clocksUntilLYCMatch() {
             debugLog("This is clocksUntilLYCMatch");
             if (this.memory.get(GBEMU_0xFF45) != 0) {
                 if (this.memory.get(GBEMU_0xFF45) > this.actualScanLine) {
                     return GBEMU_456 * (this.memory.get(GBEMU_0xFF45) - this.actualScanLine);
                 }
                 return GBEMU_456  * (GBEMU_154 - this.actualScanLine + this.memory.get(GBEMU_0xFF45));
             }
             return GBEMU_456 * (this.actualScanLine == GBEMU_153 && this.memory.get(GBEMU_0xFF44) == 0 ? GBEMU_154 : GBEMU_153 - this.actualScanLine) + GBEMU_8;
         }
         public int clocksUntilMode0() {
             debugLog("This is clocksUntilMode0");
             switch (this.modeSTAT) {
                 case 0:
                     if (this.actualScanLine == GBEMU_143) {
                         this.updateSpriteCount(0);
                         return this.spriteCount + GBEMU_5016;
                     }
                     this.updateSpriteCount(this.actualScanLine + 1);
                     return this.spriteCount + GBEMU_456;
                 case GBEMU_2:
                 case GBEMU_3:
                     this.updateSpriteCount(this.actualScanLine);
                     return this.spriteCount;
                 case 1:
                     this.updateSpriteCount(0);
                     return this.spriteCount + GBEMU_456 * (GBEMU_154 - this.actualScanLine);
                 default:
                     return 0;
             }
         }
         public void updateSpriteCount(int line) {
             this.spriteCount = GBEMU_252;
             if (this.cGBC && this.gfxSpriteShow) {
                 // Is the window enabled and are we in CGB mode?
                 int lineAdjusted = line + GBEMU_0x10;
                 int yoffset = 0;
                 int yCap = this.gfxSpriteNormalHeight ? GBEMU_0x8 : GBEMU_0x10;
                 int oamAddress = GBEMU_0xFE00;
                 while (oamAddress < GBEMU_0xFEA0 && this.spriteCount < GBEMU_312) {
                     yoffset = lineAdjusted - this.memory.get(oamAddress);
                     if (yoffset > -1 && yoffset < yCap) {
                         this.spriteCount += GBEMU_6;
                     }
                     oamAddress += GBEMU_4;
                 }
             }
         }
         public void matchLYC() {
             // LYC Register Compare
             debugLog("This is matchLYC");
             if (this.memory.get(GBEMU_0xFF44) == this.memory.get(GBEMU_0xFF45)) {
                 this.memory.set(GBEMU_0xFF41, this.memory.get(GBEMU_0xFF41) | GBEMU_0x04);
                 if (this.lycMatchTriggerSTAT) {
                     this.interruptsRequested |= GBEMU_0x2;
                     this.checkIRQMatching();
                 }
             } else {
                 this.memory.set(GBEMU_0xFF41, this.memory.get(GBEMU_0xFF41) & GBEMU_0x7B);
             }
         }
         public void updateCore() {
             debugLog("This is updateCore");
             // Update the clocking for the LCD emulation:
             this.lcdTicks += this.cpuTicks >> this.doubleSpeedShifter; // LCD Timing
             this.lcdControl[this.actualScanLine].call(this); // Scan Line and STAT Mode Control
             // Single-speed relative timing for A/V emulation:
             int timedTicks = this.cpuTicks >> this.doubleSpeedShifter; // CPU clocking can be updated from the LCD handling.
             this.audioTicks += timedTicks; // Audio Timing
             this.emulatorTicks += timedTicks; // Emulator Timing
             // CPU Timers:
             this.divTicks += this.cpuTicks; // DIV Timing
             if (this.timaEnabled) {
                 // TIMA Timing
                 this.timerTicks += this.cpuTicks;
                 while (this.timerTicks >= this.tacClocker) {
                     this.timerTicks -= this.tacClocker;
                     this.memory.set(GBEMU_0xFF05, this.memory.get(GBEMU_0xFF05) + 1);
                     if (this.memory.get(GBEMU_0xFF05) == GBEMU_0x100) {
                         this.memory.set(GBEMU_0xFF05, this.memory.get(GBEMU_0xFF06));
                         this.interruptsRequested |= GBEMU_0x4;
                         this.checkIRQMatching();
                     }
                 }
             }
             if (this.serialTimer > 0) {
                 // Serial Timing
                 // IRQ Counter:
                 this.serialTimer -= this.cpuTicks;
                 if (this.serialTimer <= 0) {
                     this.interruptsRequested |= GBEMU_0x8;
                     this.checkIRQMatching();
                 }
                 // Bit Shit Counter:
                 this.serialShiftTimer -= this.cpuTicks;
                 if (this.serialShiftTimer <= 0) {
                     this.serialShiftTimer = this.serialShiftTimerAllocated;
                     this.memory.set(GBEMU_0xFF01, ((this.memory.get(GBEMU_0xFF01) << 1) & GBEMU_0xFE) | GBEMU_0x01); // We could shift in actual link data here if we were to implement such!!!);
                 }
             }
         }
         public void updateCoreFull() {
             debugLog("This is updateCoreFull");
             // Update the state machine:
             this.updateCore();
             // End of iteration routine:
             if (this.emulatorTicks >= this.cpuCyclesTotal) {
                 this.iterationEndRoutine();
             }
         }
         public void initializeLCDController() {
             debugLog("This is initializeLCDController");
             // Display on hanlding:
             int line = 0;
             while (line < GBEMU_154) {
                 if (line < GBEMU_143) {
                     // We're on a normal scan line:
                     this.lineControl[line] = (GameBoyCore parentObj) -> {
                         if (parentObj.lcdTicks < GBEMU_80) {
                             parentObj.scanLineMode2();
                         } else if (parentObj.lcdTicks < GBEMU_252) {
                             parentObj.scanLineMode3();
                         } else if (parentObj.lcdTicks < GBEMU_456) {
                             parentObj.scanLineMode0();
                         } else {
                             // We're on a new scan line:
                             parentObj.lcdTicks -= GBEMU_456;
                             if (parentObj.statTracker != GBEMU_3) {
                                 // Make sure the mode 0 handler was run at least once per scan line:
                                 if (parentObj.statTracker != GBEMU_2) {
                                     if (parentObj.statTracker == 0 && parentObj.mode2TriggerSTAT) {
                                         parentObj.interruptsRequested |= GBEMU_0x2;
                                     }
                                     parentObj.incrementScanLineQueue();
                                 }
                                 if (parentObj.hdmaRunning) {
                                     parentObj.executeHDMA();
                                 }
                                 if (parentObj.mode0TriggerSTAT) {
                                     parentObj.interruptsRequested |= GBEMU_0x2;
                                 }
                             }
                             // Update the scanline registers and assert the LYC counter:
                             parentObj.memory.set(GBEMU_0xFF44, this.memory.get(GBEMU_0xFF44) + 1);
                             parentObj.actualScanLine = parentObj.memory.get(GBEMU_0xFF44);
                             // Perform a LYC counter assert:
                             if (parentObj.actualScanLine == parentObj.memory.get(GBEMU_0xFF45)) {
                                 parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) | GBEMU_0x04);
                                 if (parentObj.lycMatchTriggerSTAT) {
                                     parentObj.interruptsRequested |= GBEMU_0x2;
                                 }
                             } else {
                                 parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) & GBEMU_0x7B);
                             }
                             parentObj.checkIRQMatching();
                             // Reset our mode contingency variables:
                             parentObj.statTracker = 0;
                             parentObj.modeSTAT = GBEMU_2;
                             parentObj.lineControl[parentObj.actualScanLine].call(parentObj); // Scan Line and STAT Mode Control.
                         }
                     };
                 } else if (line == GBEMU_143) {
                     // We're on the last visible scan line of the LCD screen:
                     this.lineControl[GBEMU_143] = (GameBoyCore parentObj) -> {
                         if (parentObj.lcdTicks < GBEMU_80) {
                             parentObj.scanLineMode2();
                         } else if (parentObj.lcdTicks < GBEMU_252) {
                             parentObj.scanLineMode3();
                         } else if (parentObj.lcdTicks < GBEMU_456) {
                             parentObj.scanLineMode0();
                         } else {
                             // Starting V-Blank:
                             // Just finished the last visible scan line:
                             parentObj.lcdTicks -= GBEMU_456;
                             if (parentObj.statTracker != GBEMU_3) {
                                 // Make sure the mode 0 handler was run at least once per scan line:
                                 if (parentObj.statTracker != GBEMU_2) {
                                     if (parentObj.statTracker == 0 && parentObj.mode2TriggerSTAT) {
                                         parentObj.interruptsRequested |= GBEMU_0x2;
                                     }
                                     parentObj.incrementScanLineQueue();
                                 }
                                 if (parentObj.hdmaRunning) {
                                     parentObj.executeHDMA();
                                 }
                                 if (parentObj.mode0TriggerSTAT) {
                                     parentObj.interruptsRequested |= GBEMU_0x2;
                                 }
                             }
                             // Update the scanline registers and assert the LYC counter:
                             parentObj.actualScanLine = GBEMU_144;
                             parentObj.memory.set(GBEMU_0xFF44, GBEMU_144);
                             // Perform a LYC counter assert:
                             if (parentObj.memory.get(GBEMU_0xFF45) == GBEMU_144) {
                                 parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) | GBEMU_0x04);
                                 if (parentObj.lycMatchTriggerSTAT) {
                                     parentObj.interruptsRequested |= GBEMU_0x2;
                                 }
                             } else {
                                 parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) & GBEMU_0x7B);
                             }
                             // Reset our mode contingency variables:
                             parentObj.statTracker = 0;
                             // Update our state for v-blank:
                             parentObj.modeSTAT = 1;
                             parentObj.interruptsRequested |= parentObj.mode1TriggerSTAT ? GBEMU_0x3 : GBEMU_0x1;
                             parentObj.checkIRQMatching();
                             // Attempt to blit out to our canvas:
                             if (parentObj.drewBlank == 0) {
                                 // Ensure JIT framing alignment:
                                 if (parentObj.totalLinesPassed < GBEMU_144 || (parentObj.totalLinesPassed == GBEMU_144 && parentObj.midScanlineOffset > -1)) {
                                     // Make sure our gfx are up-to-date:
                                     parentObj.graphicsJITVBlank();
                                     // Draw the frame:
                                     parentObj.prepareFrame();
                                 }
                             } else {
                                 // LCD off takes at least GBEMU_2 frames:
                                 parentObj.drewBlank -= 1;
                             }
                             parentObj.lineControl[GBEMU_144].call(parentObj); // Scan Line and STAT Mode Control.
                         }
                     };
                 } else if (line < GBEMU_153) {
                     // In VBlank
                     this.lineControl[line]  = (GameBoyCore parentObj) -> {
                         if (parentObj.lcdTicks >= GBEMU_456) {
                             // We're on a new scan line:
                             parentObj.lcdTicks -= GBEMU_456;
                             parentObj.memory.set(GBEMU_0xFF44, parentObj.memory.get(GBEMU_0xFF44) + 1);
                             parentObj.actualScanLine = parentObj.memory.get(GBEMU_0xFF44);
                             // Perform a LYC counter assert:
                             if (parentObj.actualScanLine == parentObj.memory.get(GBEMU_0xFF45)) {
                                 parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) | GBEMU_0x04);
                                 if (parentObj.lycMatchTriggerSTAT) {
                                     parentObj.interruptsRequested |= GBEMU_0x2;
                                     parentObj.checkIRQMatching();
                                 }
                             } else {
                                 parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) & GBEMU_0x7B);
                             }
                             parentObj.lineControl[parentObj.actualScanLine].call(parentObj); // Scan Line and STAT Mode Control.
                         }
                     };
                 } else {
                     // VBlank Ending (We're on the last actual scan line)
                     this.lineControl[GBEMU_153] = (GameBoyCore parentObj) -> {
                         if (parentObj.lcdTicks >= GBEMU_8) {
                             if (parentObj.statTracker != GBEMU_4 && parentObj.memory.get(GBEMU_0xFF44) == GBEMU_153) {
                                 parentObj.memory.set(GBEMU_0xFF44, 0); // LY register resets to 0 early.
                                 // Perform a LYC counter assert:
                                 if (parentObj.memory.get(GBEMU_0xFF45) == 0) {
                                     parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) & GBEMU_0x04);
                                     if (parentObj.lycMatchTriggerSTAT) {
                                         parentObj.interruptsRequested |= GBEMU_0x2;
                                         parentObj.checkIRQMatching();
                                     }
                                 } else {
                                     parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) & GBEMU_0x7B);
                                 }
                                 parentObj.statTracker = GBEMU_4;
                             }
                             if (parentObj.lcdTicks >= GBEMU_456) {
                                 // We reset back to the beginning:
                                 parentObj.lcdTicks -= GBEMU_456;
                                 parentObj.statTracker = 0;
                                 parentObj.actualScanLine = 0;
                                 parentObj.lineControl[0].call(parentObj); // Scan Line and STAT Mode Control.
                             }
                         }
                     };
                 }
                 line += 1;
             }
         }
         public void displayShowOff() {
             debugLog("This is DisplayShowOff");
             if (this.drewBlank == 0) {
                 // Output a blank screen to the output framebuffer:
                 this.clearFrameBuffer();
                 this.drewFrame = true;
             }
             this.drewBlank = GBEMU_2;
         }
         public void executeHDMA() {
             this.dMAWrite(1);
             if (this.halt) {
                 if (this.lcdTicks - this.spriteCount < ((GBEMU_4 >> this.doubleSpeedShifter) | GBEMU_0x20)) {
                     // HALT clocking correction:
                     this.cpuTicks = GBEMU_4 + ((GBEMU_0x20 + this.spriteCount) << this.doubleSpeedShifter);
                     this.lcdTicks = this.spriteCount + ((GBEMU_4 >> this.doubleSpeedShifter) | GBEMU_0x20);
                 }
             } else {
                 this.lcdTicks += (GBEMU_4 >> this.doubleSpeedShifter) | GBEMU_0x20; // LCD Timing Update For HDMA.
             }
             if (this.memory.get(GBEMU_0xFF55) == 0) {
                 this.hdmaRunning = false;
                 this.memory.set(GBEMU_0xFF55, GBEMU_0xFF); // Transfer completed ('Hidden last step,' since some roms don't imply this, but most do).
             } else {
                 this.memory.set(GBEMU_0xFF55, this.memory.get(GBEMU_0xFF55) - 1);
             }
         }
         public void clockUpdate() {
             debugLog("This is clockUpdate");
             if (this.cTimeR) {
                 NewDate dateObj = new NewDate(); // The line is changed for benchmarking.
                 int newTime = dateObj.getTime();
                 int timeElapsed = newTime - this.lastIteration; // Get the numnber of milliseconds since this last executed.
                 this.lastIteration = newTime;
                 if (this.cTimeR && !this.rtcHalt) {
                     // Update the MBC3 RTC:
                     this.rtcSeconds += timeElapsed / GBEMU_1000;
                     while (this.rtcSeconds >= GBEMU_60) {
                         // System can stutter, so the seconds difference can get large, thus the 'while'.
                         this.rtcSeconds -= GBEMU_60;
                         this.rtcMinutes += 1;
                         if (this.rtcMinutes >= GBEMU_60) {
                             this.rtcMinutes -= GBEMU_60;
                             this.rtcHours += 1;
                             if (this.rtcHours >= GBEMU_24) {
                                 this.rtcHours -= GBEMU_24;
                                 this.rtcDays += 1;
                                 if (this.rtcDays >= GBEMU_512) {
                                     this.rtcDays -= GBEMU_512;
                                     this.rtcDayOverFlow = true;
                                 }
                             }
                         }
                     }
                 }
             }
         }
         public void prepareFrame() {
             debugLog("This is prepareFrame");
             // Copy the internal frame buffer to the output buffer:
             this.swizzleFrameBuffer();
             this.drewFrame = true;
         }
         public void requestDraw() {
             debugLog("This is requestDraw");
             if (this.drewFrame) {
                 this.dispatchDraw();
             }
         }
         public void dispatchDraw() {
             debugLog("This is dispatchDraw");
             int canvasRGBALength = this.offscreenRGBCount;
             if (canvasRGBALength > 0) {
                 // We actually updated the graphics internally, so copy out:
                 ArrayList<Integer> frameBuffer = canvasRGBALength == GBEMU_92160 ? this.swizzledFrame : this.resizeFrameBuffer();
                 ArrayList<Integer> canvasData = this.canvasBuffer.data;
                 int bufferIndex = 0;
                 int canvasIndex = 0;
                 while (canvasIndex < canvasRGBALength) {
                     canvasData.set(canvasIndex++, frameBuffer.get(bufferIndex++));
                     canvasData.set(canvasIndex++, frameBuffer.get(bufferIndex++));
                     canvasData.set(canvasIndex++, frameBuffer.get(bufferIndex++));
                     canvasIndex += 1;
                 }
                 this.graphicsBlit();
             }
         }
         public void swizzleFrameBuffer() {
             debugLog("This is swizzleFrameBuffer");
             // Convert our dirty GBEMU_24-bit (GBEMU_24-bit, with internal render flags above it) framebuffer to an GBEMU_8-bit buffer with separate indices for the RGB channels:
             ArrayList<Integer> frameBuffer = this.frameBuffer;
             int bufferIndex = 0;
             int canvasIndex = 0;
             while (canvasIndex < GBEMU_69120) {
                 this.swizzledFrame.set(canvasIndex++,  ((frameBuffer.get(bufferIndex) >> GBEMU_16) & GBEMU_0xFF)); // Red
                 this.swizzledFrame.set(canvasIndex++,  ((frameBuffer.get(bufferIndex) >> GBEMU_8) & GBEMU_0xFF)); // Green
                 this.swizzledFrame.set(canvasIndex++,  (frameBuffer.get(bufferIndex++) & GBEMU_0xFF)); // Blue
             }
         }
         public void clearFrameBuffer() {
             debugLog("This is clearFrameBuffer");
             int bufferIndex = 0;
             if (this.cGBC || this.colorizedGBPalettes) {
                 while (bufferIndex < GBEMU_69120) {
                     this.swizzledFrame.set(bufferIndex++, GBEMU_248);
                 }
             } else {
                 while (bufferIndex < GBEMU_69120) {
                     this.swizzledFrame.set(bufferIndex++, GBEMU_239);
                     this.swizzledFrame.set(bufferIndex++, GBEMU_255);
                     this.swizzledFrame.set(bufferIndex++, GBEMU_222);
                 }
             }
         }
         public ArrayList<Integer> resizeFrameBuffer() {
             debugLog("This is resizeFrameBuffer");
             // Return a reference to the generated resized framebuffer:
             return this.resizer.resize(this.swizzledFrame);
         }
         public void compileResizeFrameBufferFunction() {
             debugLog("This is compileResizeFrameBufferFunction");
             if (this.offscreenRGBCount > 0) {
                 this.resizer = new Resize(GBEMU_160, GBEMU_144, this.offscreenWidth, this.offscreenHeight, false, true);
             }
         }
         public void renderScanLine(int scanlineToRender) {
             this.pixelStart = scanlineToRender * GBEMU_160;
             if (this.bgEnabled) {
                 this.pixelEnd = 160;
                 this.bgLayerRender.call(scanlineToRender);
                 this.windowLayerRender.call(scanlineToRender);
             } else {
                 int pixelLine = (scanlineToRender + 1) * GBEMU_160;
                 int defaultColor = this.cGBC || this.colorizedGBPalettes ? GBEMU_0xF8F8F8 : GBEMU_0xEFFFDE;
                 int pixelPosition = scanlineToRender * GBEMU_160 + this.currentX;
                 while (pixelPosition < pixelLine) {
                     this.frameBuffer.set(pixelPosition, defaultColor);
                     pixelPosition += 1;
                 }
             }
             this.spriteLayerRender.call(scanlineToRender);
             this.currentX = 0;
             this.midScanlineOffset = -1;
         }
         public void renderMidScanLine() {
             if (this.actualScanLine < GBEMU_144 && this.modeSTAT == GBEMU_3) {
                 // TODO: Get this accurate:
                 if (this.midScanlineOffset == -1) {
                     this.midScanlineOffset = this.backgroundX & GBEMU_0x7;
                 }
                 if (this.lcdTicks >= GBEMU_82) {
                     this.pixelEnd = this.lcdTicks - GBEMU_74;
                     this.pixelEnd = Math.min(this.pixelEnd - this.midScanlineOffset - (this.pixelEnd % GBEMU_0x8), GBEMU_160);
                     if (this.bgEnabled) {
                         this.pixelStart = this.lastUnrenderedLine * GBEMU_160;
                         this.bgLayerRender.call(this.lastUnrenderedLine);
                         this.windowLayerRender.call(this.lastUnrenderedLine);
                         // TODO: Do midscanline JIT for sprites...
                     } else {
                         int pixelLine = this.lastUnrenderedLine * GBEMU_160 + this.pixelEnd;
                         int defaultColor = this.cGBC || this.colorizedGBPalettes ? GBEMU_0xF8F8F8 : GBEMU_0xEFFFDE;
                         int pixelPosition = this.lastUnrenderedLine * GBEMU_160 + this.currentX;
                         while (pixelPosition < pixelLine) {
                             this.frameBuffer.set(pixelPosition, defaultColor);
                             pixelPosition += 1;
                         }
                     }
                     this.currentX = this.pixelEnd;
                 }
             }
         }
         public void initializeModeSpecificArrays() {
             debugLog("This is initializeModeSpecificArrays");
             this.lcdControl = this.lcdIsOn ? this.lineControl : this.disPlayOffControl;
             if (this.cGBC) {
                 this.gbcOBJRawPalette = this.getTypedArray(GBEMU_0x40, 0, "uint8");
                 this.gbcBGRawPalette = this.getTypedArray(GBEMU_0x40, 0, "uint8");
                 this.gbcOBJPalette = this.getTypedArray(GBEMU_0x20, GBEMU_0x1000000, "int32");
                 this.gbcBGPalette = this.getTypedArray(GBEMU_0x40, 0, "int32");
                 this.bgCHRBank2.array = this.getTypedArray(GBEMU_0x800, 0, "uint8");
                 this.bgCHRCurrentBank = this.currvramBank > 0 ? this.bgCHRBank2 : this.bgCHRBank1;
                 this.tileCache = this.generateCacheArray(GBEMU_0xf80);
             } else {
                 this.gbOBJPalette = this.getTypedArray(GBEMU_8, 0, "int32");
                 this.gbBGPalette = this.getTypedArray(GBEMU_4, 0, "int32");
                 this.bgPalette = this.gbBGPalette;
                 this.objPalette = this.gbOBJPalette;
                 this.tileCache = this.generateCacheArray(GBEMU_0x700);
                 this.sortBuffer = this.getTypedArray(GBEMU_0x100, 0, "uint8");
                 this.oamAddressCache = this.getTypedArray(GBEMU_10, 0, "int32");
             }
             this.renderPathBuild();
         }
         public void gBCtoGBModeAdjust() {
             debugLog("This is GBCtoGBModeAdjust");
             cout("Stepping down from GBC mode.", 0);
             this.bgCHRBank2.array = new ArrayList<Integer>();
             this.vram = new ArrayList<Integer>();
             this.gbcMemory = new ArrayList<Integer>();
             this.bgCHRCurrentBank.array = new ArrayList<Integer>();
             for (int index = 0; index < GBEMU_0x700; index++) {
                 this.tileCache.add(new ArrayObject());
             }
             if ((boolean) settings[GBEMU_4]) {
                 this.gbBGColorizedPalette = this.getTypedArray(GBEMU_4, 0, "int32");
                 this.gbOBJColorizedPalette = this.getTypedArray(GBEMU_8, 0, "int32");
                 this.cachedBGPaletteConversion = this.getTypedArray(GBEMU_4, 0, "int32");
                 this.cachedOBJPaletteConversion = this.getTypedArray(GBEMU_8, 0, "int32");
                 this.bgPalette = this.gbBGColorizedPalette;
                 this.objPalette = this.gbOBJColorizedPalette;
                 this.gbOBJPalette = null;
                 this.gbBGPalette = null;
                 this.getGBCColor();
             } else {
                 this.gbOBJPalette = this.getTypedArray(GBEMU_8, 0, "int32");
                 this.gbBGPalette = this.getTypedArray(GBEMU_4, 0, "int32");
                 this.bgPalette = this.gbBGPalette;
                 this.objPalette = this.gbOBJPalette;
             }
             this.sortBuffer = this.getTypedArray(GBEMU_0x100, 0, "uint8");
             this.oamAddressCache = this.getTypedArray(GBEMU_10, 0, "int32");
             this.renderPathBuild();
             this.memoryReadJumpCompile();
             this.memoryWriteJumpCompile();
         }
         public void renderPathBuild() {
             debugLog("This is renderPathBuild");
             if (!this.cGBC) {
                 this.bgLayerRender = GameBoyCore::bGGBLayerRender;
                 this.windowLayerRender = GameBoyCore::windowGBLayerRender;
                 this.spriteLayerRender = GameBoyCore::spriteGBLayerRender;
             } else {
                 this.priorityFlaggingPathRebuild();
                 this.spriteLayerRender = GameBoyCore::spriteGBCLayerRender;
             }
         }
         public void priorityFlaggingPathRebuild() {
             debugLog("This is priorityFlaggingPathRebuild");
             if (this.bgPriorityEnabled) {
                 this.bgLayerRender = GameBoyCore::bGGBCLayerRender;
                 this.windowLayerRender = GameBoyCore::windowGBCLayerRender;
             } else {
                 this.bgLayerRender = GameBoyCore::bGGBCLayerRenderNoPriorityFlagging;
                 this.windowLayerRender = GameBoyCore::windowGBCLayerRenderNoPriorityFlagging;
             }
         }
         public int rGBTint(int value) {
             // Adjustment for the GBC's tinting (According to Gambatte):
             int r = value & GBEMU_0x1f;
             int g = (value >> GBEMU_5) & GBEMU_0x1f;
             int b = (value >> GBEMU_10) & GBEMU_0x1f;
             return (((r * GBEMU_13 + g * GBEMU_2 + b) >> 1) << GBEMU_16) | ((g * GBEMU_3 + b) << GBEMU_9) | ((r * GBEMU_3 + g * GBEMU_2 + b * GBEMU_11) >> 1);
         }
         public void getGBCColor() {
             debugLog("This is getGBCColor");
             // GBC Colorization of DMG roms:
             // BG
             int counter = 0;
             while (counter < GBEMU_4) {
                 int adjustedIndex = counter << 1;
                 // BG
                 this.cachedBGPaletteConversion.set(counter, this.rGBTint((this.gbcBGRawPalette.get(adjustedIndex | 1) << GBEMU_8) | this.gbcBGRawPalette.get(adjustedIndex)));
                 // OBJ 1
                 this.cachedOBJPaletteConversion.set(counter, this.rGBTint((this.gbcOBJRawPalette.get(adjustedIndex | 1) << GBEMU_8) | this.gbcOBJRawPalette.get(adjustedIndex)));
                 counter += 1;
             }
             // OBJ GBEMU_2
             counter = GBEMU_4;
             while (counter < GBEMU_8) {
                 int adjustedIndex = counter << 1;
                 this.cachedOBJPaletteConversion.set(counter, this.rGBTint((this.gbcOBJRawPalette.get(adjustedIndex | 1) << GBEMU_8) | this.gbcOBJRawPalette.get(adjustedIndex)));
                 counter += 1;
             }
             // Update the palette entries:
             this.updateGBBGPalette = GameBoyCore::updateGBColorizedBGPalette;
             this.updateGBOBJPalette = GameBoyCore::updateGBColorizedOBJPalette;
             this.updateGBBGPalette.call(this.memory.get(GBEMU_0xFF47));
             this.updateGBOBJPalette.call(0, this.memory.get(GBEMU_0xFF48));
             this.updateGBOBJPalette.call(1, this.memory.get(GBEMU_0xFF49));
             this.colorizedGBPalettes = true;
         }
         public void updateGBRegularBGPalette(int data) {
             debugLog("This is updateGBRegularBGPalette");
             this.gbBGPalette.set(0, this.colors[data & GBEMU_0x03] | GBEMU_0x2000000);
             this.gbBGPalette.set(1, this.colors[(data >> GBEMU_2) & GBEMU_0x03]);
             this.gbBGPalette.set(GBEMU_2, this.colors[(data >> GBEMU_4) & GBEMU_0x03]);
             this.gbBGPalette.set(GBEMU_3, this.colors[data >> GBEMU_6]);
         }
         public static void updateGBColorizedBGPalette(int data) {
             debugLog("This is updateGBColorizedBGPalette");
             // GB colorization:
             gbBGColorizedPalette.set(0, cachedBGPaletteConversion.get(data & GBEMU_0x03) | GBEMU_0x2000000);
             gbBGColorizedPalette.set(1, cachedBGPaletteConversion.get((data >> GBEMU_2) & GBEMU_0x03));
             gbBGColorizedPalette.set(GBEMU_2, cachedBGPaletteConversion.get((data >> GBEMU_4) & GBEMU_0x03));
             gbBGColorizedPalette.set(GBEMU_3, cachedBGPaletteConversion.get(data >> GBEMU_6));
         };
         public static void updateGBRegularOBJPalette(int index, int data) {
             debugLog("This is updateGBRegularOBJPalette");
             gbOBJPalette.set(index | 1, colors[(data >> GBEMU_2) & GBEMU_0x03]);
             gbOBJPalette.set(index | GBEMU_2, colors[(data >> GBEMU_4) & GBEMU_0x03]);
             gbOBJPalette.set(index | GBEMU_3, colors[data >> GBEMU_6]);
         };
         public static void updateGBColorizedOBJPalette(int index, int data) {
             debugLog("This is updateGBColorizedOBJPalette");
             // GB colorization:
             gbOBJColorizedPalette.set(index | 1, cachedOBJPaletteConversion.get(index | ((data >> GBEMU_2) & GBEMU_0x03)));
             gbOBJColorizedPalette.set(index | GBEMU_2, cachedOBJPaletteConversion.get(index | ((data >> GBEMU_4) & GBEMU_0x03)));
             gbOBJColorizedPalette.set(index | GBEMU_3, cachedOBJPaletteConversion.get(index | (data >> GBEMU_6)));
         };
         public void updateGBCBGPalette(int indexTemp, int dataTemp) {
             int index = indexTemp;
             int data = dataTemp;
             if (this.gbcBGRawPalette.get(index) != data) {
                 this.midScanLineJIT();
                 // Update the color palette for BG tiles since it changed:
                 this.gbcBGRawPalette.set(index, data);
                 if ((index & GBEMU_0x06) == 0) {
                     // Palette 0 (Special tile Priority stuff)
                     data = GBEMU_0x2000000 | this.rGBTint((this.gbcBGRawPalette.get(index | 1) << GBEMU_8) | this.gbcBGRawPalette.get(index & GBEMU_0x3E));
                     index >>= 1;
                     this.gbcBGPalette.set(index, data);
                     this.gbcBGPalette.set(GBEMU_0x20 | index, GBEMU_0x1000000 | data);
                 } else {
                     // Regular Palettes (No special crap)
                     data = this.rGBTint((this.gbcBGRawPalette.get(index | 1) << GBEMU_8) | this.gbcBGRawPalette.get(index & GBEMU_0x3E));
                     index >>= 1;
                     this.gbcBGPalette.set(index, data);
                     this.gbcBGPalette.set(GBEMU_0x20 | index, GBEMU_0x1000000 | data);
                 }
             }
         }
         public void updateGBCOBJPalette(int index, int data) {
             if (this.gbcOBJRawPalette.get(index) != data) {
                 // Update the color palette for OBJ tiles since it changed:
                 this.gbcOBJRawPalette.set(index, data);
                 if ((index & GBEMU_0x06) > 0) {
                     // Regular Palettes (No special crap)
                     this.midScanLineJIT();
                     this.gbcOBJPalette.set(index >> 1,
                             GBEMU_0x1000000 | this.rGBTint((this.gbcOBJRawPalette.get(index | 1) << GBEMU_8) | this.gbcOBJRawPalette.get(index & GBEMU_0x3E)));
                 }
             }
         }
         public static void bGGBLayerRender(int scanlineToRender) {
             debugLog("This is BGGBLayerRender");
             int scrollYAdjusted = (backgroundY + scanlineToRender) & GBEMU_0xFF; // The line of the BG we're at.
             int tileYLine = (scrollYAdjusted & GBEMU_7) << GBEMU_3;
             int tileYDown = gfxBackgroundCHRBankPosition | ((scrollYAdjusted & GBEMU_0xF8) << GBEMU_2); // The row of cached tiles we're fetching from.
             int scrollXAdjusted = (backgroundX + currentX) & GBEMU_0xFF; // The scroll amount of the BG.
             int pixelPosition = pixelStart + currentX; // Current pixel we're working on.
             int pixelPositionEnd =
                     pixelStart +
                             (gfxWindowDisplay && scanlineToRender - windowY >= 0 ? Math.min(Math.max(windowX, 0) + currentX, pixelEnd) : pixelEnd); // Make sure we do at most 160 pixels a scanline.
             int tileNumber = tileYDown + (scrollXAdjusted >> GBEMU_3);
             int chrCode = bgCHRBank1.array.get(tileNumber);
             if (chrCode < gfxBackgroundBankOffset) {
                 chrCode |= GBEMU_0x100;
             }
             ArrayList<Integer> tile = tileCache.get(chrCode).array;
             int texel = scrollXAdjusted & GBEMU_0x7;
             while (texel < GBEMU_8 && pixelPosition < pixelPositionEnd && scrollXAdjusted < GBEMU_0x100) {
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(tileYLine | texel++)));
                 scrollXAdjusted += 1;
             }
             int scrollXAdjustedAligned = Math.min(pixelPositionEnd - pixelPosition, GBEMU_0x100 - scrollXAdjusted) >> GBEMU_3;
             scrollXAdjusted += scrollXAdjustedAligned << GBEMU_3;
             scrollXAdjustedAligned += tileNumber;
             while (tileNumber < scrollXAdjustedAligned) {
                 tileNumber += 1;
                 chrCode = bgCHRBank1.array.get(tileNumber);
                 if (chrCode < gfxBackgroundBankOffset) {
                     chrCode |= GBEMU_0x100;
                 }
                 tile = tileCache.get(chrCode).array;
                 texel = tileYLine;
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel)));
             }
             if (pixelPosition < pixelPositionEnd) {
                 if (scrollXAdjusted < GBEMU_0x100) {
                     tileNumber += 1;
                     chrCode = bgCHRBank1.array.get(tileNumber);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     tile = tileCache.get(chrCode).array;
                     texel = tileYLine - 1;
                     while (pixelPosition < pixelPositionEnd && scrollXAdjusted < GBEMU_0x100) {
                         texel += 1;
                         frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel)));
                         scrollXAdjusted += 1;
                     }
                 }
                 scrollXAdjustedAligned = ((pixelPositionEnd - pixelPosition) >> GBEMU_3) + tileYDown;
                 while (tileYDown < scrollXAdjustedAligned) {
                     chrCode = bgCHRBank1.array.get(tileYDown++);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     tile = tileCache.get(chrCode).array;
                     texel = tileYLine;
                     frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel)));
                 }
                 if (pixelPosition < pixelPositionEnd) {
                     chrCode = bgCHRBank1.array.get(tileYDown);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     tile = tileCache.get(chrCode).array;
                     switch (pixelPositionEnd - pixelPosition) {
                         case GBEMU_7:
                             frameBuffer.set(pixelPosition + GBEMU_6, bgPalette.get(tile.get(tileYLine | GBEMU_6)));
                         case GBEMU_6:
                             frameBuffer.set(pixelPosition + GBEMU_5, bgPalette.get(tile.get(tileYLine | GBEMU_5)));
                         case GBEMU_5:
                             frameBuffer.set(pixelPosition + GBEMU_4, bgPalette.get(tile.get(tileYLine | GBEMU_4)));
                         case GBEMU_4:
                             frameBuffer.set(pixelPosition + GBEMU_3, bgPalette.get(tile.get(tileYLine | GBEMU_3)));
                         case GBEMU_3:
                             frameBuffer.set(pixelPosition + GBEMU_2, bgPalette.get(tile.get(tileYLine | GBEMU_2)));
                         case GBEMU_2:
                             frameBuffer.set(pixelPosition + 1, bgPalette.get(tile.get(tileYLine | 1)));
                         case 1:
                             frameBuffer.set(pixelPosition, bgPalette.get(tile.get(tileYLine)));
                         default:
                             break;
                     }
                 }
             }
         };
         public static void bGGBCLayerRender(int bGGBC_scanlineToRender) {
             int scrollYAdjusted = (backgroundY + bGGBC_scanlineToRender) & GBEMU_0xFF; // The line of the BG we're at.
             int tileYLine = (scrollYAdjusted & GBEMU_7) << GBEMU_3;
             int tileYDown = gfxBackgroundCHRBankPosition | ((scrollYAdjusted & GBEMU_0xF8) << GBEMU_2); // The row of cached tiles we're fetching from.
             int scrollXAdjusted = (backgroundX + currentX) & GBEMU_0xFF; // The scroll amount of the BG.
             int pixelPosition = pixelStart + currentX; // Current pixel we're working on.
             int pixelPositionEnd =
                     pixelStart +
                             (gfxWindowDisplay && bGGBC_scanlineToRender - windowY >= 0 ? Math.min(Math.max(windowX, 0) +currentX, pixelEnd) : pixelEnd); // Make sure we do at most 160 pixels a scanline.
             int tileNumber = tileYDown + (scrollXAdjusted >> GBEMU_3);
             int chrCode = bgCHRBank1.array.get(tileNumber);
             if (chrCode < gfxBackgroundBankOffset) {
                 chrCode |= GBEMU_0x100;
             }
             int attrCode = bgCHRBank2.array.get(tileNumber);
             ArrayList<Integer> tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
             int palette = ((attrCode & GBEMU_0x7) << GBEMU_2) | ((attrCode & GBEMU_0x80) >> GBEMU_2);
             int texel = scrollXAdjusted & GBEMU_0x7;
             while (texel < GBEMU_8 && pixelPosition < pixelPositionEnd && scrollXAdjusted < GBEMU_0x100) {
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(tileYLine | texel++)));
                 scrollXAdjusted += 1;
             }
             int scrollXAdjustedAligned = Math.min(pixelPositionEnd - pixelPosition, GBEMU_0x100 - scrollXAdjusted) >> GBEMU_3;
             scrollXAdjusted += scrollXAdjustedAligned << GBEMU_3;
             scrollXAdjustedAligned += tileNumber;
             while (tileNumber < scrollXAdjustedAligned) {
                 tileNumber += 1;
                 chrCode = bgCHRBank1.array.get(tileNumber);
                 if (chrCode < gfxBackgroundBankOffset) {
                     chrCode |= GBEMU_0x100;
                 }
                 attrCode = bgCHRBank2.array.get(tileNumber);
                 tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                 palette = ((attrCode & GBEMU_0x7) << GBEMU_2) | ((attrCode & GBEMU_0x80) >> GBEMU_2);
                 texel = tileYLine;
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel)));
             }
             if (pixelPosition < pixelPositionEnd) {
                 if (scrollXAdjusted < GBEMU_0x100) {
                     tileNumber += 1;
                     chrCode = bgCHRBank1.array.get(tileNumber);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     attrCode = bgCHRBank2.array.get(tileNumber);
                     tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                     palette = ((attrCode & GBEMU_0x7) << GBEMU_2) | ((attrCode & GBEMU_0x80) >> GBEMU_2);
                     texel = tileYLine - 1;
                     while (pixelPosition < pixelPositionEnd && scrollXAdjusted < GBEMU_0x100) {
                         texel += 1;
                         frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel)));
                         scrollXAdjusted += 1;
                     }
                 }
                 scrollXAdjustedAligned = ((pixelPositionEnd - pixelPosition) >> GBEMU_3) + tileYDown;
                 while (tileYDown < scrollXAdjustedAligned) {
                     chrCode = bgCHRBank1.array.get(tileYDown);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     attrCode = bgCHRBank2.array.get(tileYDown++);
                     tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                     palette = ((attrCode & GBEMU_0x7) << GBEMU_2) | ((attrCode & GBEMU_0x80) >> GBEMU_2);
                     texel = tileYLine;
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel)));
                 }
                 if (pixelPosition < pixelPositionEnd) {
                     chrCode = bgCHRBank1.array.get(tileYDown);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     attrCode = bgCHRBank2.array.get(tileYDown);
                     tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                     palette = ((attrCode & GBEMU_0x7) << GBEMU_2) | ((attrCode & GBEMU_0x80) >> GBEMU_2);
                     switch (pixelPositionEnd - pixelPosition) {
                         case GBEMU_7:
                             frameBuffer.set(pixelPosition + GBEMU_6, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_6)));
                         case GBEMU_6:
                             frameBuffer.set(pixelPosition + GBEMU_5, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_5)));
                         case GBEMU_5:
                             frameBuffer.set(pixelPosition + GBEMU_4, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_4)));
                         case GBEMU_4:
                             frameBuffer.set(pixelPosition + GBEMU_3, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_3)));
                         case GBEMU_3:
                             frameBuffer.set(pixelPosition + GBEMU_2, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_2)));
                         case GBEMU_2:
                             frameBuffer.set(pixelPosition + 1, gbcBGPalette.get(palette | tile.get(tileYLine | 1)));
                         case 1:
                             frameBuffer.set(pixelPosition, gbcBGPalette.get(palette | tile.get(tileYLine)));
                         default:
                             break;
                     }
                 }
             }
         };
         public static void bGGBCLayerRenderNoPriorityFlagging(int scanlineToRender) {
             debugLog("This is BGGBCLayerRenderNoPriorityFlagging");
             int scrollYAdjusted = (backgroundY + scanlineToRender) & GBEMU_0xFF; // The line of the BG we're at.
             int tileYLine = (scrollYAdjusted & GBEMU_7) << GBEMU_3;
             int tileYDown = gfxBackgroundCHRBankPosition | ((scrollYAdjusted & GBEMU_0xF8) << GBEMU_2); // The row of cached tiles // we're fetching from.
             int scrollXAdjusted = (backgroundX + currentX) & GBEMU_0xFF; // The scroll amount of the BG.
             int pixelPosition = pixelStart + currentX; // Current pixel we're working on.
             int pixelPositionEnd = pixelStart +
                     (gfxWindowDisplay && scanlineToRender - windowY >= 0
                             ? Math.min(Math.max(windowX, 0) + currentX, pixelEnd) : pixelEnd); // Make sure we do at most 160 pixels a scanline.
             int tileNumber = tileYDown + (scrollXAdjusted >> GBEMU_3);
             int chrCode = bgCHRBank1.array.get(tileNumber);
             if (chrCode < gfxBackgroundBankOffset) {
                 chrCode |= GBEMU_0x100;
             }
             int attrCode = bgCHRBank2.array.get(tileNumber);
             ArrayList<Integer> tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
             int palette = (attrCode & GBEMU_0x7) << GBEMU_2;
             int texel = scrollXAdjusted & GBEMU_0x7;
             while (texel < GBEMU_8 && pixelPosition < pixelPositionEnd && scrollXAdjusted < GBEMU_0x100) {
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(tileYLine | texel++)));
                 scrollXAdjusted += 1;
             }
             int scrollXAdjustedAligned = Math.min(pixelPositionEnd - pixelPosition, GBEMU_0x100 - scrollXAdjusted) >> GBEMU_3;
             scrollXAdjusted += scrollXAdjustedAligned << GBEMU_3;
             scrollXAdjustedAligned += tileNumber;
             while (tileNumber < scrollXAdjustedAligned) {
                 tileNumber += 1;
                 chrCode = bgCHRBank1.array.get(tileNumber);
                 if (chrCode < gfxBackgroundBankOffset) {
                     chrCode |= GBEMU_0x100;
                 }
                 attrCode = bgCHRBank2.array.get(tileNumber);
                 tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                 palette = (attrCode & GBEMU_0x7) << GBEMU_2;
                 texel = tileYLine;
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                 frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel)));
             }
             if (pixelPosition < pixelPositionEnd) {
                 if (scrollXAdjusted < GBEMU_0x100) {
                     tileNumber += 1;
                     chrCode = bgCHRBank1.array.get(tileNumber);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     attrCode = bgCHRBank2.array.get(tileNumber);
                     tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                     palette = (attrCode & GBEMU_0x7) << GBEMU_2;
                     texel = tileYLine - 1;
                     while (pixelPosition < pixelPositionEnd && scrollXAdjusted < GBEMU_0x100) {
                         texel += 1;
                         frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel)));
                         scrollXAdjusted += 1;
                     }
                 }
                 scrollXAdjustedAligned = ((pixelPositionEnd - pixelPosition) >> GBEMU_3) + tileYDown;
                 while (tileYDown < scrollXAdjustedAligned) {
                     chrCode = bgCHRBank1.array.get(tileYDown);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     attrCode = bgCHRBank2.array.get(tileYDown++);
                     tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                     palette = (attrCode & GBEMU_0x7) << GBEMU_2;
                     texel = tileYLine;
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                     frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel)));
                 }
                 if (pixelPosition < pixelPositionEnd) {
                     chrCode = bgCHRBank1.array.get(tileYDown);
                     if (chrCode < gfxBackgroundBankOffset) {
                         chrCode |= GBEMU_0x100;
                     }
                     attrCode = bgCHRBank2.array.get(tileYDown);
                     tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                     palette = (attrCode & GBEMU_0x7) << GBEMU_2;
                     switch (pixelPositionEnd - pixelPosition) {
                         case GBEMU_7:
                             frameBuffer.set(pixelPosition + GBEMU_6, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_6)));
                         case GBEMU_6:
                             frameBuffer.set(pixelPosition + GBEMU_5, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_5)));
                         case GBEMU_5:
                             frameBuffer.set(pixelPosition + GBEMU_4, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_4)));
                         case GBEMU_4:
                             frameBuffer.set(pixelPosition + GBEMU_3, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_3)));
                         case GBEMU_3:
                             frameBuffer.set(pixelPosition + GBEMU_2, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_2)));
                         case GBEMU_2:
                             frameBuffer.set(pixelPosition + 1, gbcBGPalette.get(palette | tile.get(tileYLine | 1)));
                         case 1:
                             frameBuffer.set(pixelPosition, gbcBGPalette.get(palette | tile.get(tileYLine)));
                         default:
                             break;
                     }
                 }
             }
         };
         public static void windowGBLayerRender(int scanlineToRender) {
             debugLog("This is WindowGBLayerRender");
             if (gfxWindowDisplay) {
                 // Is the window enabled?
                 int scrollYAdjusted = scanlineToRender - windowY; // The line of the BG we're at.
                 if (scrollYAdjusted >= 0) {
                     int scrollXRangeAdjusted = windowX > 0 ? windowX + currentX : currentX;
                     int pixelPosition = pixelStart + scrollXRangeAdjusted;
                     int pixelPositionEnd = pixelStart + pixelEnd;
                     if (pixelPosition < pixelPositionEnd) {
                         int tileYLine = (scrollYAdjusted & GBEMU_0x7) << GBEMU_3;
                         int tileNumber = (gfxWindowCHRBankPosition | ((scrollYAdjusted & GBEMU_0xF8) << GBEMU_2)) + (currentX >> GBEMU_3);
                         int chrCode = bgCHRBank1.array.get(tileNumber);
                         if (chrCode < gfxBackgroundBankOffset) {
                             chrCode |= GBEMU_0x100;
                         }
                         ArrayList<Integer> tile = tileCache.get(chrCode).array;
                         int texel = (scrollXRangeAdjusted - windowX) & GBEMU_0x7;
                         scrollXRangeAdjusted = Math.min(GBEMU_8, texel + pixelPositionEnd - pixelPosition);
                         while (texel < scrollXRangeAdjusted) {
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(tileYLine | texel++)));
                         }
                         scrollXRangeAdjusted = tileNumber + ((pixelPositionEnd - pixelPosition) >> GBEMU_3);
                         while (tileNumber < scrollXRangeAdjusted) {
                             tileNumber += 1;
                             chrCode = bgCHRBank1.array.get(tileNumber);
                             if (chrCode < gfxBackgroundBankOffset) {
                                 chrCode |= GBEMU_0x100;
                             }
                             tile = tileCache.get(chrCode).array;
                             texel = tileYLine;
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, bgPalette.get(tile.get(texel)));
                         }
                         if (pixelPosition < pixelPositionEnd) {
                             tileNumber += 1;
                             chrCode = bgCHRBank1.array.get(tileNumber);
                             if (chrCode < gfxBackgroundBankOffset) {
                                 chrCode |= GBEMU_0x100;
                             }
                             tile = tileCache.get(chrCode).array;
                             switch (pixelPositionEnd - pixelPosition) {
                                 case GBEMU_7:
                                     frameBuffer.set(pixelPosition + GBEMU_6, bgPalette.get(tile.get(tileYLine | GBEMU_6)));
                                 case GBEMU_6:
                                     frameBuffer.set(pixelPosition + GBEMU_5, bgPalette.get(tile.get(tileYLine | GBEMU_5)));
                                 case GBEMU_5:
                                     frameBuffer.set(pixelPosition + GBEMU_4, bgPalette.get(tile.get(tileYLine | GBEMU_4)));
                                 case GBEMU_4:
                                     frameBuffer.set(pixelPosition + GBEMU_3, bgPalette.get(tile.get(tileYLine | GBEMU_3)));
                                 case GBEMU_3:
                                     frameBuffer.set(pixelPosition + GBEMU_2, bgPalette.get(tile.get(tileYLine | GBEMU_2)));
                                 case GBEMU_2:
                                     frameBuffer.set(pixelPosition + 1, bgPalette.get(tile.get(tileYLine | 1)));
                                 case 1:
                                     frameBuffer.set(pixelPosition, bgPalette.get(tile.get(tileYLine)));
                                 default:
                                     break;
                             }
                         }
                     }
                 }
             }
         };
         public static void windowGBCLayerRender(int scanlineToRender) {
             if (gfxWindowDisplay) {
                 // Is the window enabled?
                 int scrollYAdjusted = scanlineToRender - windowY; // The line of the BG we're at.
                 if (scrollYAdjusted >= 0) {
                     int scrollXRangeAdjusted = windowX > 0 ? windowX + currentX : currentX;
                     int pixelPosition = pixelStart + scrollXRangeAdjusted;
                     int pixelPositionEnd = pixelStart + pixelEnd;
                     if (pixelPosition < pixelPositionEnd) {
                         int tileYLine = (scrollYAdjusted & GBEMU_0x7) << GBEMU_3;
                         int tileNumber = (gfxWindowCHRBankPosition | ((scrollYAdjusted & GBEMU_0xF8) << GBEMU_2)) + (currentX >> GBEMU_3);
                         int chrCode = bgCHRBank1.array.get(tileNumber);
                         if (chrCode < gfxBackgroundBankOffset) {
                             chrCode |= GBEMU_0x100;
                         }
                         int attrCode = bgCHRBank2.array.get(tileNumber);
                         ArrayList<Integer> tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                         int palette = ((attrCode & GBEMU_0x7) << GBEMU_2) | ((attrCode & GBEMU_0x80) >> GBEMU_2);
                         int texel = (scrollXRangeAdjusted - windowX) & GBEMU_0x7;
                         scrollXRangeAdjusted = Math.min(GBEMU_8, texel + pixelPositionEnd - pixelPosition);
                         while (texel < scrollXRangeAdjusted) {
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(tileYLine | texel++)));
                         }
                         scrollXRangeAdjusted = tileNumber + ((pixelPositionEnd - pixelPosition) >> GBEMU_3);
                         while (tileNumber < scrollXRangeAdjusted) {
                             tileNumber += 1;
                             chrCode = bgCHRBank1.array.get(tileNumber);
                             if (chrCode < gfxBackgroundBankOffset) {
                                 chrCode |= GBEMU_0x100;
                             }
                             attrCode = bgCHRBank2.array.get(tileNumber);
                             tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                             palette = ((attrCode & GBEMU_0x7) << GBEMU_2) | ((attrCode & GBEMU_0x80) >> GBEMU_2);
                             texel = tileYLine;
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel)));
                         }
                         if (pixelPosition < pixelPositionEnd) {
                             tileNumber += 1;
                             chrCode = bgCHRBank1.array.get(tileNumber);
                             if (chrCode < gfxBackgroundBankOffset) {
                                 chrCode |= GBEMU_0x100;
                             }
                             attrCode = bgCHRBank2.array.get(tileNumber);
                             tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                             palette = ((attrCode & GBEMU_0x7) << GBEMU_2) | ((attrCode & GBEMU_0x80) >> GBEMU_2);
                             switch (pixelPositionEnd - pixelPosition) {
                                 case GBEMU_7:
                                     frameBuffer.set(pixelPosition + GBEMU_6, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_6)));
                                 case GBEMU_6:
                                     frameBuffer.set(pixelPosition + GBEMU_5, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_5)));
                                 case GBEMU_5:
                                     frameBuffer.set(pixelPosition + GBEMU_4, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_4)));
                                 case GBEMU_4:
                                     frameBuffer.set(pixelPosition + GBEMU_3, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_3)));
                                 case GBEMU_3:
                                     frameBuffer.set(pixelPosition + GBEMU_2, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_2)));
                                 case GBEMU_2:
                                     frameBuffer.set(pixelPosition + 1, gbcBGPalette.get(palette | tile.get(tileYLine | 1)));
                                 case 1:
                                     frameBuffer.set(pixelPosition, gbcBGPalette.get(palette | tile.get(tileYLine)));
                                 default:
                                     break;
                             }
                         }
                     }
                 }
             }
         };
         public static void windowGBCLayerRenderNoPriorityFlagging(int scanlineToRender) {
             debugLog("This is WindowGBCLayerRenderNoPriorityFlagging");
             if (gfxWindowDisplay) {
                 int scrollYAdjusted = scanlineToRender - windowY; // The line of the BG we're at.
                 if (scrollYAdjusted >= 0) {
                     int scrollXRangeAdjusted = windowX > 0 ? windowX + currentX : currentX;
                     int pixelPosition = pixelStart + scrollXRangeAdjusted;
                     int pixelPositionEnd = pixelStart + pixelEnd;
                     if (pixelPosition < pixelPositionEnd) {
                         int tileYLine = (scrollYAdjusted & GBEMU_0x7) << GBEMU_3;
                         int tileNumber = (gfxWindowCHRBankPosition | ((scrollYAdjusted & GBEMU_0xF8) << GBEMU_2)) + (currentX >> GBEMU_3);
                         int chrCode = bgCHRBank1.array.get(tileNumber);
                         if (chrCode < gfxBackgroundBankOffset) {
                             chrCode |= GBEMU_0x100;
                         }
                         int attrCode = bgCHRBank2.array.get(tileNumber);
                         ArrayList<Integer> tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                         int palette = (attrCode & GBEMU_0x7) << GBEMU_2;
                         int texel = (scrollXRangeAdjusted - windowX) & GBEMU_0x7;
                         scrollXRangeAdjusted = Math.min(GBEMU_8, texel + pixelPositionEnd - pixelPosition);
                         while (texel < scrollXRangeAdjusted) {
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(tileYLine | texel++)));
                         }
                         scrollXRangeAdjusted = tileNumber + ((pixelPositionEnd - pixelPosition) >> GBEMU_3);
                         while (tileNumber < scrollXRangeAdjusted) {
                             tileNumber += 1;
                             chrCode = bgCHRBank1.array.get(tileNumber);
                             if (chrCode < gfxBackgroundBankOffset) {
                                 chrCode |= GBEMU_0x100;
                             }
                             attrCode = bgCHRBank2.array.get(tileNumber);
                             tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                             palette = (attrCode & GBEMU_0x7) << GBEMU_2;
                             texel = tileYLine;
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel++)));
                             frameBuffer.set(pixelPosition++, gbcBGPalette.get(palette | tile.get(texel)));
                         }
                         if (pixelPosition < pixelPositionEnd) {
                             tileNumber += 1;
                             chrCode = bgCHRBank1.array.get(tileNumber);
                             if (chrCode < gfxBackgroundBankOffset) {
                                 chrCode |= GBEMU_0x100;
                             }
                             attrCode = bgCHRBank2.array.get(tileNumber);
                             tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | chrCode).array;
                             palette = (attrCode & GBEMU_0x7) << GBEMU_2;
                             switch (pixelPositionEnd - pixelPosition) {
                                 case GBEMU_7:
                                     frameBuffer.set(pixelPosition + GBEMU_6, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_6)));
                                 case GBEMU_6:
                                     frameBuffer.set(pixelPosition + GBEMU_5, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_5)));
                                 case GBEMU_5:
                                     frameBuffer.set(pixelPosition + GBEMU_4, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_4)));
                                 case GBEMU_4:
                                     frameBuffer.set(pixelPosition + GBEMU_3, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_3)));
                                 case GBEMU_3:
                                     frameBuffer.set(pixelPosition + GBEMU_2, gbcBGPalette.get(palette | tile.get(tileYLine | GBEMU_2)));
                                 case GBEMU_2:
                                     frameBuffer.set(pixelPosition + 1, gbcBGPalette.get(palette | tile.get(tileYLine | 1)));
                                 case 1:
                                     frameBuffer.set(pixelPosition, gbcBGPalette.get(palette | tile.get(tileYLine)));
                                 default:
                                     break;
                             }
                         }
                     }
                 }
             }
         };
         public static void spriteGBLayerRender(int scanlineToRender) {
             debugLog("This is SpriteGBLayerRender");
             if (gfxSpriteShow) {
                 // Are sprites enabled?
                 int lineAdjusted = scanlineToRender + GBEMU_0x10;
                 int oamAddress = GBEMU_0xFE00;
                 int yoffset = 0;
                 int xcoord = 1;
                 int xCoordStart = 0;
                 int xCoordEnd = 0;
                 int attrCode = 0;
                 int palette = 0;
                 ArrayList<Integer> tile = new ArrayList<>();
                 int data = 0;
                 int spriteCount = 0;
                 int length = 0;
                 int currentPixel = 0;
                 int linePixel = 0;
                 // Clear our x-coord sort buffer:
                 while (xcoord < GBEMU_168) {
                     sortBuffer.set(xcoord++, GBEMU_0xFF);
                 }
                 if (gfxSpriteNormalHeight) {
                     // Draw the visible sprites:
                     length = findLowestSpriteDrawable(lineAdjusted, GBEMU_0x7);
                     while (spriteCount < length) {
                         oamAddress = oamAddressCache.get(spriteCount);
                         yoffset = (lineAdjusted - memory.get(oamAddress)) << GBEMU_3;
                         attrCode = memory.get(oamAddress | GBEMU_3);
                         palette = (attrCode & GBEMU_0x10) >> GBEMU_2;
                         tile = tileCache.get(((attrCode & GBEMU_0x60) << GBEMU_4) | memory.get(oamAddress | GBEMU_0x2)).array;
                         linePixel = memory.get(oamAddress | 1);
                         xCoordStart = memory.get(oamAddress | 1);
                         xCoordEnd = Math.min(GBEMU_168 - linePixel, GBEMU_8);
                         xcoord = linePixel > GBEMU_7 ? 0 : GBEMU_8 - linePixel;
                         currentPixel = pixelStart + (linePixel > GBEMU_8 ? linePixel - GBEMU_8 : 0);
                         while (xcoord < xCoordEnd) {
                             if (sortBuffer.get(linePixel) > xCoordStart) {
                                 if (frameBuffer.get(currentPixel) >= GBEMU_0x2000000) {
                                     data = tile.get(yoffset | xcoord);
                                     if (data > 0) {
                                         frameBuffer.set(currentPixel, objPalette.get(palette | data));
                                         sortBuffer.set(linePixel, xCoordStart);
                                     }
                                 } else if (frameBuffer.get(currentPixel) < GBEMU_0x1000000) {
                                     data = tile.get(yoffset | xcoord);
                                     if (data > 0 && attrCode < GBEMU_0x80) {
                                         frameBuffer.set(currentPixel, objPalette.get(palette | data));
                                         sortBuffer.set(linePixel, xCoordStart);
                                     }
                                 }
                             }
                             xcoord += 1;
                             currentPixel += 1;
                             linePixel += 1;
                         }
                         spriteCount += 1;
                     }
                 } else {
                     // Draw the visible sprites:
                     length = findLowestSpriteDrawable(lineAdjusted, GBEMU_0xF);
                     while (spriteCount < length) {
                         oamAddress = oamAddressCache.get(spriteCount);
                         yoffset = (lineAdjusted - memory.get(oamAddress)) << GBEMU_3;
                         attrCode = memory.get(oamAddress | GBEMU_3);
                         palette = (attrCode & GBEMU_0x10) >> GBEMU_2;
                         if ((attrCode & GBEMU_0x40) == (GBEMU_0x40 & yoffset)) {
                             tile = tileCache.get(((attrCode & GBEMU_0x60) << GBEMU_4) | (memory.get(oamAddress | GBEMU_0x2) & GBEMU_0xFE)).array;
                         } else {
                             tile = tileCache.get(((attrCode & GBEMU_0x60) << GBEMU_4) | memory.get(oamAddress | GBEMU_0x2) | 1).array;
                         }
                         yoffset &= GBEMU_0x3F;
                         xCoordStart = memory.get(oamAddress | 1);
                         linePixel = xCoordStart;
                         xCoordEnd = Math.min(GBEMU_168 - linePixel, GBEMU_8);
                         xcoord = linePixel > GBEMU_7 ? 0 : GBEMU_8 - linePixel;
                         currentPixel = pixelStart + (linePixel > GBEMU_8 ? linePixel - GBEMU_8 : 0);
                         while (xcoord < xCoordEnd) {
                             if (sortBuffer.get(linePixel) > xCoordStart) {
                                 if (frameBuffer.get(currentPixel) >= GBEMU_0x2000000) {
                                     data = tile.get(yoffset | xcoord);
                                     if (data > 0) {
                                         frameBuffer.set(currentPixel, objPalette.get(palette | data));
                                         sortBuffer.set(linePixel, xCoordStart);
                                     }
                                 } else if (frameBuffer.get(currentPixel) < GBEMU_0x1000000) {
                                     data = tile.get(yoffset | xcoord);
                                     if (data > 0 && attrCode < GBEMU_0x80) {
                                         frameBuffer.set(currentPixel, objPalette.get(palette | data));
                                         sortBuffer.set(linePixel, xCoordStart);
                                     }
                                 }
                             }
                             xcoord += 1;
                             currentPixel += 1;
                             linePixel += 1;
                         }
                         spriteCount += 1;
                     }
                 }
             }
         };
         public static int findLowestSpriteDrawable(int scanlineToRender, int drawableRange) {
             debugLog("This is findLowestSpriteDrawable");
             int address = GBEMU_0xFE00;
             int spriteCount = 0;
             int diff = 0;
             while (address < GBEMU_0xFEA0 && spriteCount < GBEMU_10) {
                 diff = scanlineToRender - memory.get(address);
                 if ((diff & drawableRange) == diff) {
                     oamAddressCache.set(spriteCount++, address);
                 }
                 address += GBEMU_4;
             }
             return spriteCount;
         }
         public static void spriteGBCLayerRender(int scanlineToRender) {
             if (gfxSpriteShow) {
                 // Are sprites enabled?
                 int oamAddress = GBEMU_0xFE00;
                 int lineAdjusted = scanlineToRender + GBEMU_0x10;
                 int yoffset = 0;
                 int xcoord = 0;
                 int endX = 0;
                 int xCounter = 0;
                 int attrCode = 0;
                 int palette = 0;
                 ArrayList<Integer> tile = null;
                 int data = 0;
                 int currentPixel = 0;
                 int spriteCount = 0;
                 if (gfxSpriteNormalHeight) {
                     while (oamAddress < GBEMU_0xFEA0 && spriteCount < GBEMU_10) {
                         yoffset = lineAdjusted - memory.get(oamAddress);
                         if ((yoffset & GBEMU_0x7) == yoffset) {
                             xcoord = memory.get(oamAddress | 1) - GBEMU_8;
                             endX = Math.min(GBEMU_160, xcoord + GBEMU_8);
                             attrCode = memory.get(oamAddress | GBEMU_3);
                             palette = (attrCode & GBEMU_7) << GBEMU_2;
                             tile = tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | memory.get(oamAddress | GBEMU_2)).array;
                             xCounter = xcoord > 0 ? xcoord : 0;
                             xcoord -= yoffset << GBEMU_3;
                             currentPixel = pixelStart + xCounter;
                             while (xCounter < endX) {
                                 if (frameBuffer.get(currentPixel) >= GBEMU_0x2000000) {
                                     data = tile.get(xCounter - xcoord);
                                     if (data > 0) {
                                         frameBuffer.set(currentPixel, gbcOBJPalette.get(palette | data));
                                     }
                                 } else if (frameBuffer.get(currentPixel) < GBEMU_0x1000000) {
                                     data = tile.get(xCounter - xcoord);
                                     if (data > 0 && attrCode < GBEMU_0x80) {
                                         // Don't optimize for attrCode, as LICM-capable JITs should optimize its checks.
                                         frameBuffer.set(currentPixel, gbcOBJPalette.get(palette | data));
                                     }
                                 }
                                 xCounter += 1;
                                 currentPixel += 1;
                             }
                             spriteCount += 1;
                         }
                         oamAddress += GBEMU_4;
                     }
                 } else {
                     while (oamAddress < GBEMU_0xFEA0 && spriteCount < GBEMU_10) {
                         yoffset = lineAdjusted - memory.get(oamAddress);
                         if ((yoffset & GBEMU_0xF) == yoffset) {
                             xcoord = memory.get(oamAddress | 1) - GBEMU_8;
                             endX = Math.min(GBEMU_160, xcoord + GBEMU_8);
                             attrCode = memory.get(oamAddress | GBEMU_3);
                             palette = (attrCode & GBEMU_7) << GBEMU_2;
                             if ((attrCode & GBEMU_0x40) == (GBEMU_0x40 & (yoffset << GBEMU_3))) {
                                 tile =
                                         tileCache.get(
                                                 ((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | (memory.get(oamAddress | GBEMU_0x2) & GBEMU_0xfe)
                                         ).array;
                             } else {
                                 tile =
                                         tileCache.get(((attrCode & GBEMU_0x08) << GBEMU_8) | ((attrCode & GBEMU_0x60) << GBEMU_4) | memory.get(oamAddress | GBEMU_0x2) | 1).array;
                             }
                             xCounter = xcoord > 0 ? xcoord : 0;
                             xcoord -= (yoffset & GBEMU_0x7) << GBEMU_3;
                             currentPixel = pixelStart + xCounter;
                             while (xCounter < endX) {
                                 if (frameBuffer.get(currentPixel) >= GBEMU_0x2000000) {
                                     data = tile.get(xCounter - xcoord);
                                     if (data > 0) {
                                         frameBuffer.set(currentPixel, gbcOBJPalette.get(palette | data));
                                     }
                                 } else if (frameBuffer.get(currentPixel) < GBEMU_0x1000000) {
                                     data = tile.get(xCounter - xcoord);
                                     if (data > 0 && attrCode < GBEMU_0x80) {
                                         // Don't optimize for attrCode, as LICM-capable JITs should optimize its checks.
                                         frameBuffer.set(currentPixel, gbcOBJPalette.get(palette | data));
                                     }
                                 }
                                 xCounter += 1;
                                 currentPixel += 1;
                             }
                             spriteCount += 1;
                         }
                         oamAddress += GBEMU_4;
                     }
                 }
             }
         }
         // Generate only a single tile line for the GB tile cache mode:
         public void generateGBTileLine(int addressTemp) {
             debugLog("This is generateGBTileLine");
             int address = addressTemp;
             int lineCopy = (this.memory.get(GBEMU_0x1 | address) << GBEMU_8) | this.memory.get(GBEMU_0x9FFE & address);
             ArrayObject tileBlock = this.tileCache.get((address & GBEMU_0x1FF0) >> GBEMU_4);
             address = (address & GBEMU_0xE) << GBEMU_2;
             tileBlock.array.set(address | GBEMU_7, ((lineCopy & GBEMU_0x100) >> GBEMU_7) | (lineCopy & GBEMU_0x1));
             tileBlock.array.set(address | GBEMU_6, ((lineCopy & GBEMU_0x200) >> GBEMU_8) | ((lineCopy & GBEMU_0x2) >> 1));
             tileBlock.array.set(address | GBEMU_5, ((lineCopy & GBEMU_0x400) >> GBEMU_9) | ((lineCopy & GBEMU_0x4) >> GBEMU_2));
             tileBlock.array.set(address | GBEMU_4, ((lineCopy & GBEMU_0x800) >> GBEMU_10) | ((lineCopy & GBEMU_0x8) >> GBEMU_3));
             tileBlock.array.set(address | GBEMU_3, ((lineCopy & GBEMU_0x1000) >> GBEMU_11) | ((lineCopy & GBEMU_0x10) >> GBEMU_4));
             tileBlock.array.set(address | GBEMU_2, ((lineCopy & GBEMU_0x2000) >> GBEMU_12) | ((lineCopy & GBEMU_0x20) >> GBEMU_5));
             tileBlock.array.set(address | 1, ((lineCopy & GBEMU_0x4000) >> GBEMU_13) | ((lineCopy & GBEMU_0x40) >> GBEMU_6));
             tileBlock.array.set(address, ((lineCopy & GBEMU_0x8000) >> GBEMU_14) | ((lineCopy & GBEMU_0x80) >> GBEMU_7));
         }
         // Generate only a single tile line for the GBC tile cache mode (Bank 1):
         public void generateGBCTileLineBank1(int addressTemp) {
             int address = addressTemp;
             int lineCopy = (this.memory.get(GBEMU_0x1 | address) << GBEMU_8) | this.memory.get(GBEMU_0x9FFE & address);
             address &= GBEMU_0x1FFE;
             ArrayObject tileBlock1 = this.tileCache.get(address >> GBEMU_4);
             ArrayObject tileBlock2 = this.tileCache.get(GBEMU_0x200 | (address >> GBEMU_4));
             ArrayObject tileBlock3 = this.tileCache.get(GBEMU_0x400 | (address >> GBEMU_4));
             ArrayObject tileBlock4 = this.tileCache.get(GBEMU_0x600 | (address >> GBEMU_4));
             address = (address & GBEMU_0xE) << GBEMU_2;
             int addressFlipped = GBEMU_0x38 - address;
             tileBlock1.array.set(address | GBEMU_7, ((lineCopy & GBEMU_0x100) >> GBEMU_7) | (lineCopy & GBEMU_0x1));
             tileBlock4.array.set(addressFlipped, tileBlock1.array.get(address | GBEMU_7));
             tileBlock2.array.set(address, tileBlock1.array.get(address | GBEMU_7));
             tileBlock3.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address | GBEMU_7));
             tileBlock1.array.set(address | GBEMU_6, ((lineCopy & GBEMU_0x200) >> GBEMU_8) | ((lineCopy & GBEMU_0x2) >> 1));
             tileBlock4.array.set(addressFlipped | 1, tileBlock1.array.get(address | GBEMU_6));
             tileBlock2.array.set(address | 1, tileBlock1.array.get(address | GBEMU_6));
             tileBlock3.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | GBEMU_6));
             tileBlock1.array.set(address | GBEMU_5, ((lineCopy & GBEMU_0x400) >> GBEMU_9) | ((lineCopy & GBEMU_0x4) >> GBEMU_2));
             tileBlock4.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
             tileBlock2.array.set(address | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
             tileBlock3.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_5));
             tileBlock1.array.set(address | GBEMU_4, ((lineCopy & GBEMU_0x800) >> GBEMU_10) | ((lineCopy & GBEMU_0x8) >> GBEMU_3));
             tileBlock4.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
             tileBlock2.array.set(address | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
             tileBlock3.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_4));
             tileBlock1.array.set(address | GBEMU_3, ((lineCopy & GBEMU_0x1000) >> GBEMU_11) | ((lineCopy & GBEMU_0x10) >> GBEMU_4));
             tileBlock4.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
             tileBlock2.array.set(address | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
             tileBlock3.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_3));
             tileBlock1.array.set(address | GBEMU_2, ((lineCopy & GBEMU_0x2000) >> GBEMU_12) | ((lineCopy & GBEMU_0x20) >> GBEMU_5));
             tileBlock4.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
             tileBlock2.array.set(address | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
             tileBlock3.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_2));
             tileBlock1.array.set(address | 1, ((lineCopy & GBEMU_0x4000) >> GBEMU_13) | ((lineCopy & GBEMU_0x40) >> GBEMU_6));
             tileBlock4.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | 1));
             tileBlock2.array.set(address | GBEMU_6, tileBlock1.array.get(address | 1));
             tileBlock3.array.set(addressFlipped | 1, tileBlock1.array.get(address | 1));
             tileBlock1.array.set(address, ((lineCopy & GBEMU_0x8000) >> GBEMU_14) | ((lineCopy & GBEMU_0x80) >> GBEMU_7));
             tileBlock4.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address));
             tileBlock2.array.set(address | GBEMU_7, tileBlock1.array.get(address));
             tileBlock3.array.set(addressFlipped, tileBlock1.array.get(address));
         }
         // Generate all the flip combinations for a full GBC vram bank 1 tile:
         public void generateGBCTileBank1(int vramAddressTemp) {
             int vramAddress = vramAddressTemp;
             int address = vramAddress >> GBEMU_4;
             ArrayObject tileBlock1 = this.tileCache.get(address);
             ArrayObject tileBlock2 = this.tileCache.get(GBEMU_0x200 | address);
             ArrayObject tileBlock3 = this.tileCache.get(GBEMU_0x400 | address);
             ArrayObject tileBlock4 = this.tileCache.get(GBEMU_0x600 | address);
             int lineCopy = 0;
             vramAddress |= GBEMU_0x8000;
             address = 0;
             int addressFlipped = 56;
             do {
                 lineCopy = (this.memory.get(GBEMU_0x1 | vramAddress) << GBEMU_8) | this.memory.get(vramAddress);
                 tileBlock1.array.set(address | GBEMU_7, ((lineCopy & GBEMU_0x100) >> GBEMU_7) | (lineCopy & GBEMU_0x1));
                 tileBlock4.array.set(addressFlipped, tileBlock1.array.get(address | GBEMU_7));
                 tileBlock2.array.set(address, tileBlock1.array.get(address | GBEMU_7));
                 tileBlock3.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address | GBEMU_7));
                 tileBlock1.array.set(address | GBEMU_6, ((lineCopy & GBEMU_0x200) >> GBEMU_8) | ((lineCopy & GBEMU_0x2) >> 1));
                 tileBlock4.array.set(addressFlipped | 1, tileBlock1.array.get(address | GBEMU_6));
                 tileBlock2.array.set(address | 1, tileBlock1.array.get(address | GBEMU_6));
                 tileBlock3.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | GBEMU_6));
                 tileBlock1.array.set(address | GBEMU_5, ((lineCopy & GBEMU_0x400) >> GBEMU_9) | ((lineCopy & GBEMU_0x4) >> GBEMU_2));
                 tileBlock4.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
                 tileBlock2.array.set(address | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
                 tileBlock3.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_5));
                 tileBlock1.array.set(address | GBEMU_4, ((lineCopy & GBEMU_0x800) >> GBEMU_10) | ((lineCopy & GBEMU_0x8) >> GBEMU_3));
                 tileBlock4.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
                 tileBlock2.array.set(address | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
                 tileBlock3.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_4));
                 tileBlock1.array.set(address | GBEMU_3, ((lineCopy & GBEMU_0x1000) >> GBEMU_11) | ((lineCopy & GBEMU_0x10) >> GBEMU_4));
                 tileBlock4.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
                 tileBlock2.array.set(address | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
                 tileBlock3.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_3));
                 tileBlock1.array.set(address | GBEMU_2, ((lineCopy & GBEMU_0x2000) >> GBEMU_12) | ((lineCopy & GBEMU_0x20) >> GBEMU_5));
                 tileBlock4.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
                 tileBlock2.array.set(address | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
                 tileBlock3.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_2));
                 tileBlock1.array.set(address | 1, ((lineCopy & GBEMU_0x4000) >> GBEMU_13) | ((lineCopy & GBEMU_0x40) >> GBEMU_6));
                 tileBlock4.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | 1));
                 tileBlock2.array.set(address | GBEMU_6, tileBlock1.array.get(address | 1));
                 tileBlock3.array.set(addressFlipped | 1, tileBlock1.array.get(address | 1));
                 tileBlock1.array.set(address, ((lineCopy & GBEMU_0x8000) >> GBEMU_14) | ((lineCopy & GBEMU_0x80) >> GBEMU_7));
                 tileBlock4.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address));
                 tileBlock2.array.set(address | GBEMU_7, tileBlock1.array.get(address));
                 tileBlock3.array.set(addressFlipped, tileBlock1.array.get(address));
                 address += GBEMU_8;
                 addressFlipped -= GBEMU_8;
                 vramAddress += GBEMU_2;
             } while (addressFlipped > -1);
         }
         // Generate only a single tile line for the GBC tile cache mode (Bank GBEMU_2):
         public void generateGBCTileLineBank2(int addressTemp) {
             debugLog("This is generateGBCTileLineBank2");
             int address = addressTemp;
             int lineCopy = (this.vram.get(GBEMU_0x1 | address) << GBEMU_8) | this.vram.get(GBEMU_0x1FFE & address);
             ArrayObject tileBlock1 = this.tileCache.get(GBEMU_0x800 | (address >> GBEMU_4));
             ArrayObject tileBlock2 = this.tileCache.get(GBEMU_0xA00 | (address >> GBEMU_4));
             ArrayObject tileBlock3 = this.tileCache.get(GBEMU_0xC00 | (address >> GBEMU_4));
             ArrayObject tileBlock4 = this.tileCache.get(GBEMU_0xE00 | (address >> GBEMU_4));
             address = (address & GBEMU_0xE) << GBEMU_2;
             int addressFlipped = GBEMU_0x38 - address;
             tileBlock1.array.set(address | GBEMU_7, ((lineCopy & GBEMU_0x100) >> GBEMU_7) | (lineCopy & GBEMU_0x1));
             tileBlock4.array.set(addressFlipped, tileBlock1.array.get(address | GBEMU_7));
             tileBlock2.array.set(address, tileBlock1.array.get(address | GBEMU_7));
             tileBlock3.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address | GBEMU_7));
             tileBlock1.array.set(address | GBEMU_6, ((lineCopy & GBEMU_0x200) >> GBEMU_8) | ((lineCopy & GBEMU_0x2) >> 1));
             tileBlock4.array.set(addressFlipped | 1, tileBlock1.array.get(address | GBEMU_6));
             tileBlock2.array.set(address | 1, tileBlock1.array.get(address | GBEMU_6));
             tileBlock3.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | GBEMU_6));
             tileBlock1.array.set(address | GBEMU_5, ((lineCopy & GBEMU_0x400) >> GBEMU_9) | ((lineCopy & GBEMU_0x4) >> GBEMU_2));
             tileBlock4.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
             tileBlock2.array.set(address | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
             tileBlock3.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_5));
             tileBlock1.array.set(address | GBEMU_4, ((lineCopy & GBEMU_0x800) >> GBEMU_10) | ((lineCopy & GBEMU_0x8) >> GBEMU_3));
             tileBlock4.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
             tileBlock2.array.set(address | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
             tileBlock3.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_4));
             tileBlock1.array.set(address | GBEMU_3, ((lineCopy & GBEMU_0x1000) >> GBEMU_11) | ((lineCopy & GBEMU_0x10) >> GBEMU_4));
             tileBlock4.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
             tileBlock2.array.set(address | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
             tileBlock3.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_3));
             tileBlock1.array.set(address | GBEMU_2, ((lineCopy & GBEMU_0x2000) >> GBEMU_12) | ((lineCopy & GBEMU_0x20) >> GBEMU_5));
             tileBlock4.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
             tileBlock2.array.set(address | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
             tileBlock3.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_2));
             tileBlock1.array.set(address | 1, ((lineCopy & GBEMU_0x4000) >> GBEMU_13) | ((lineCopy & GBEMU_0x40) >> GBEMU_6));
             tileBlock4.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | 1));
             tileBlock2.array.set(address | GBEMU_6, tileBlock1.array.get(address | 1));
             tileBlock3.array.set(addressFlipped | 1, tileBlock1.array.get(address | 1));
             tileBlock1.array.set(address, ((lineCopy & GBEMU_0x8000) >> GBEMU_14) | ((lineCopy & GBEMU_0x80) >> GBEMU_7));
             tileBlock4.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address));
             tileBlock2.array.set(address | GBEMU_7, tileBlock1.array.get(address));
             tileBlock3.array.set(addressFlipped, tileBlock1.array.get(address));
         }
         // Generate all the flip combinations for a full GBC vram bank GBEMU_2 tile:
         public void generateGBCTileBank2(int vramAddressTemp) {
             int vramAddress = vramAddressTemp;
             int address = vramAddress >> GBEMU_4;
             ArrayObject tileBlock1 = this.tileCache.get(GBEMU_0x800 | address);
             ArrayObject tileBlock2 = this.tileCache.get(GBEMU_0xA00 | address);
             ArrayObject tileBlock3 = this.tileCache.get(GBEMU_0xC00 | address);
             ArrayObject tileBlock4 = this.tileCache.get(GBEMU_0xE00 | address);
             int lineCopy = 0;
             address = 0;
             int addressFlipped = 56;
             do {
                 lineCopy = (this.vram.get(GBEMU_0x1 | vramAddress) << GBEMU_8) | this.vram.get(vramAddress);
                 tileBlock1.array.set(address | GBEMU_7, ((lineCopy & GBEMU_0x100) >> GBEMU_7) | (lineCopy & GBEMU_0x1));
                 tileBlock4.array.set(addressFlipped, tileBlock1.array.get(address | GBEMU_7));
                 tileBlock2.array.set(address, tileBlock1.array.get(address | GBEMU_7));
                 tileBlock3.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address | GBEMU_7));
                 tileBlock1.array.set(address | GBEMU_6, ((lineCopy & GBEMU_0x200) >> GBEMU_8) | ((lineCopy & GBEMU_0x2) >> 1));
                 tileBlock4.array.set(addressFlipped | 1, tileBlock1.array.get(address | GBEMU_6));
                 tileBlock2.array.set(address | 1, tileBlock1.array.get(address | GBEMU_6));
                 tileBlock3.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | GBEMU_6));
                 tileBlock1.array.set(address | GBEMU_5, ((lineCopy & GBEMU_0x400) >> GBEMU_9) | ((lineCopy & GBEMU_0x4) >> GBEMU_2));
                 tileBlock4.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
                 tileBlock2.array.set(address | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
                 tileBlock3.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_5));
                 tileBlock1.array.set(address | GBEMU_4, ((lineCopy & GBEMU_0x800) >> GBEMU_10) | ((lineCopy & GBEMU_0x8) >> GBEMU_3));
                 tileBlock4.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
                 tileBlock2.array.set(address | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
                 tileBlock3.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_4));
                 tileBlock1.array.set(address | GBEMU_3, ((lineCopy & GBEMU_0x1000) >> GBEMU_11) | ((lineCopy & GBEMU_0x10) >> GBEMU_4));
                 tileBlock4.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
                 tileBlock2.array.set(address | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
                 tileBlock3.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_3));
                 tileBlock1.array.set(address | GBEMU_2, ((lineCopy & GBEMU_0x2000) >> GBEMU_12) | ((lineCopy & GBEMU_0x20) >> GBEMU_5));
                 tileBlock4.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
                 tileBlock2.array.set(address | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
                 tileBlock3.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_2));
                 tileBlock1.array.set(address | 1, ((lineCopy & GBEMU_0x4000) >> GBEMU_13) | ((lineCopy & GBEMU_0x40) >> GBEMU_6));
                 tileBlock4.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | 1));
                 tileBlock2.array.set(address | GBEMU_6, tileBlock1.array.get(address | 1));
                 tileBlock3.array.set(addressFlipped | 1, tileBlock1.array.get(address | 1));
                 tileBlock1.array.set(address, ((lineCopy & GBEMU_0x8000) >> GBEMU_14) | ((lineCopy & GBEMU_0x80) >> GBEMU_7));
                 tileBlock4.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address));
                 tileBlock2.array.set(address | GBEMU_7, tileBlock1.array.get(address));
                 tileBlock3.array.set(addressFlipped, tileBlock1.array.get(address));
                 address += GBEMU_8;
                 addressFlipped -= GBEMU_8;
                 vramAddress += GBEMU_2;
             } while (addressFlipped > -1);
         }
         // Generate only a single tile line for the GB tile cache mode (OAM accessible range):
         public void generateGBOAMTileLine(int addressTemp) {
             debugLog("This is generateGBOAMTileLine");
             int address = addressTemp;
             int lineCopy = (this.memory.get(GBEMU_0x1 | address) << GBEMU_8) | this.memory.get(GBEMU_0x9FFE & address);
             address &= GBEMU_0x1FFE;
             ArrayObject tileBlock1 = this.tileCache.get(address >> GBEMU_4);
             ArrayObject tileBlock2 = this.tileCache.get(GBEMU_0x200 | (address >> GBEMU_4));
             ArrayObject tileBlock3 = this.tileCache.get(GBEMU_0x400 | (address >> GBEMU_4));
             ArrayObject tileBlock4 = this.tileCache.get(GBEMU_0x600 | (address >> GBEMU_4));
             address = (address & GBEMU_0xE) << GBEMU_2;
             int addressFlipped = GBEMU_0x38 - address;
             tileBlock1.array.set(address | GBEMU_7, ((lineCopy & GBEMU_0x100) >> GBEMU_7) | (lineCopy & GBEMU_0x1));
             tileBlock4.array.set(addressFlipped, tileBlock1.array.get(address | GBEMU_7));
             tileBlock2.array.set(address, tileBlock1.array.get(address | GBEMU_7));
             tileBlock3.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address | GBEMU_7));
             tileBlock1.array.set(address | GBEMU_6, ((lineCopy & GBEMU_0x200) >> GBEMU_8) | ((lineCopy & GBEMU_0x2) >> 1));
             tileBlock4.array.set(addressFlipped | 1, tileBlock1.array.get(address | GBEMU_6));
             tileBlock2.array.set(address | 1, tileBlock1.array.get(address | GBEMU_6));
             tileBlock3.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | GBEMU_6));
             tileBlock1.array.set(address | GBEMU_5, ((lineCopy & GBEMU_0x400) >> GBEMU_9) | ((lineCopy & GBEMU_0x4) >> GBEMU_2));
             tileBlock4.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
             tileBlock2.array.set(address | GBEMU_2, tileBlock1.array.get(address | GBEMU_5));
             tileBlock3.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_5));
             tileBlock1.array.set(address | GBEMU_4, ((lineCopy & GBEMU_0x800) >> GBEMU_10) | ((lineCopy & GBEMU_0x8) >> GBEMU_3));
             tileBlock4.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
             tileBlock2.array.set(address | GBEMU_3, tileBlock1.array.get(address | GBEMU_4));
             tileBlock3.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_4));
             tileBlock1.array.set(address | GBEMU_3, ((lineCopy & GBEMU_0x1000) >> GBEMU_11) | ((lineCopy & GBEMU_0x10) >> GBEMU_4));
             tileBlock4.array.set(addressFlipped | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
             tileBlock2.array.set(address | GBEMU_4, tileBlock1.array.get(address | GBEMU_3));
             tileBlock3.array.set(addressFlipped | GBEMU_3, tileBlock1.array.get(address | GBEMU_3));
             tileBlock1.array.set(address | GBEMU_2, ((lineCopy & GBEMU_0x2000) >> GBEMU_12) | ((lineCopy & GBEMU_0x20) >> GBEMU_5));
             tileBlock4.array.set(addressFlipped | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
             tileBlock2.array.set(address | GBEMU_5, tileBlock1.array.get(address | GBEMU_2));
             tileBlock3.array.set(addressFlipped | GBEMU_2, tileBlock1.array.get(address | GBEMU_2));
             tileBlock1.array.set(address | 1, ((lineCopy & GBEMU_0x4000) >> GBEMU_13) | ((lineCopy & GBEMU_0x40) >> GBEMU_6));
             tileBlock4.array.set(addressFlipped | GBEMU_6, tileBlock1.array.get(address | 1));
             tileBlock2.array.set(address | GBEMU_6, tileBlock1.array.get(address | 1));
             tileBlock3.array.set(addressFlipped | 1, tileBlock1.array.get(address | 1));
             tileBlock1.array.set(address, ((lineCopy & GBEMU_0x8000) >> GBEMU_14) | ((lineCopy & GBEMU_0x80) >> GBEMU_7));
             tileBlock4.array.set(addressFlipped | GBEMU_7, tileBlock1.array.get(address));
             tileBlock2.array.set(address | GBEMU_7, tileBlock1.array.get(address));
             tileBlock3.array.set(addressFlipped, tileBlock1.array.get(address));
         }
         public void graphicsJIT() {
             if (this.lcdIsOn) {
                 this.totalLinesPassed = 0; // Mark frame for ensuring a JIT pass for the next framebuffer output.
                 this.graphicsJITScanlineGroup();
             }
         }
         public void graphicsJITVBlank() {
             debugLog("This is graphicsJITVBlank");
             // JIT the graphics to v-blank framing:
             this.totalLinesPassed += this.queuedScanLines;
             this.graphicsJITScanlineGroup();
         }
         public void graphicsJITScanlineGroup() {
             // Normal rendering JIT, where we try to do groups of scanlines at once:
             while (this.queuedScanLines > 0) {
                 this.renderScanLine(this.lastUnrenderedLine);
                 if (this.lastUnrenderedLine < GBEMU_143) {
                     this.lastUnrenderedLine += 1;
                 } else {
                     this.lastUnrenderedLine = 0;
                 }
                 this.queuedScanLines -= 1;
             }
         }
         public void incrementScanLineQueue() {
             if (this.queuedScanLines < GBEMU_144) {
                 this.queuedScanLines += 1;
             } else {
                 this.currentX = 0;
                 this.midScanlineOffset = -1;
                 if (this.lastUnrenderedLine < GBEMU_143) {
                     this.lastUnrenderedLine += 1;
                 } else {
                     this.lastUnrenderedLine = 0;
                 }
             }
         }
         public void midScanLineJIT() {
             this.graphicsJIT();
             this.renderMidScanLine();
         }
         // Check for the highest priority IRQ to fire:
         public void launchIRQ() {
             debugLog("This is launchIRQ");
             int bitShift = 0;
             int testbit = 1;
             do {
                 // Check to see if an interrupt is enabled AND requested.
                 if ((testbit & this.irqLineMatched) == testbit) {
                     this.ime = false; // Reset the interrupt enabling.
                     this.interruptsRequested -= testbit; // Reset the interrupt request.
                     this.irqLineMatched = GBEMU_0; // Reset the IRQ assertion.
                     // Interrupts have a certain clock cycle length:
                     this.cpuTicks = GBEMU_20;
                     // Set the stack pointer to the current program counter value:
                     this.stackPointer = (this.stackPointer - 1) & GBEMU_0xFFFF;
                     this.memoryWriter.get(this.stackPointer).call(this, this.stackPointer, this.programCounter >> GBEMU_8);
                     this.stackPointer = (this.stackPointer - 1) & GBEMU_0xFFFF;
                     this.memoryWriter.get(this.stackPointer).call(this, this.stackPointer, this.programCounter & GBEMU_0xFF);
                     // Set the program counter to the interrupt's address:
                     this.programCounter = GBEMU_0x40 | (bitShift << GBEMU_3);
                     // Clock the core for mid-instruction updates:
                     this.updateCore();
                     return; // We only want the highest priority interrupt.
                 }
                 bitShift += 1;
                 testbit = 1 << bitShift;
             } while (bitShift < GBEMU_5);
         }
         /*
          * Check for IRQs to be fired while not in HALT:
          */
         public void checkIRQMatching() {
             if (this.ime) {
                 this.irqLineMatched = this.interruptsEnabled & this.interruptsRequested & GBEMU_0x1f;
             }
         }
 
         public void calculateHALTPeriod() {
             debugLog("This is calculateHALTPeriod");
             // Initialize our variables and start our prediction:
             int currentClocks = 0;
             if (!this.halt) {
                 this.halt = true;
                 currentClocks = -1;
                 int tempVar = 0;
                 if (this.lcdIsOn) {
                     // If the LCD is enabled, then predict the LCD IRQs enabled:
                     if ((this.interruptsEnabled & GBEMU_0x1) == GBEMU_0x1) {
                         currentClocks = (GBEMU_456 * ((this.modeSTAT == 1 ? GBEMU_298 : GBEMU_144) - this.actualScanLine) - this.lcdTicks) << this.doubleSpeedShifter;
                     }
                     if ((this.interruptsEnabled & GBEMU_0x2) == GBEMU_0x2) {
                         if (this.mode0TriggerSTAT) {
                             tempVar = (this.clocksUntilMode0() - this.lcdTicks) << this.doubleSpeedShifter;
                             if (tempVar <= currentClocks || currentClocks == -1) {
                                 currentClocks = tempVar;
                             }
                         }
                         if (this.mode1TriggerSTAT && (this.interruptsEnabled & GBEMU_0x1) == 0) {
                             tempVar = (GBEMU_456 * ((this.modeSTAT == 1 ? GBEMU_298 : GBEMU_144) - this.actualScanLine) - this.lcdTicks) << this.doubleSpeedShifter;
                             if (tempVar <= currentClocks || currentClocks == -1) {
                                 currentClocks = tempVar;
                             }
                         }
                         if (this.mode2TriggerSTAT) {
                             tempVar =
                                     ((this.actualScanLine >= GBEMU_143 ? GBEMU_456 * (GBEMU_154 - this.actualScanLine) : GBEMU_456) - this.lcdTicks) << this.doubleSpeedShifter;
                             if (tempVar <= currentClocks || currentClocks == -1) {
                                 currentClocks = tempVar;
                             }
                         }
                         if (this.lycMatchTriggerSTAT && this.memory.get(GBEMU_0xFF45) <= GBEMU_153) {
                             tempVar = (this.clocksUntilLYCMatch() - this.lcdTicks) << this.doubleSpeedShifter;
                             if (tempVar <= currentClocks || currentClocks == -1) {
                                 currentClocks = tempVar;
                             }
                         }
                     }
                 }
                 if (this.timaEnabled && (this.interruptsEnabled & GBEMU_0x4) == GBEMU_0x4) {
                     // CPU timer IRQ prediction:
                     tempVar = (GBEMU_0x100 - this.memory.get(GBEMU_0xFF05)) * this.tacClocker - this.timerTicks;
                     if (tempVar <= currentClocks || currentClocks == -1) {
                         currentClocks = tempVar;
                     }
                 }
                 if (this.serialTimer > 0 && (this.interruptsEnabled & GBEMU_0x8) == GBEMU_0x8) {
                     // Serial IRQ prediction:
                     if (this.serialTimer <= currentClocks || currentClocks == -1) {
                         currentClocks = this.serialTimer;
                     }
                 }
             } else {
                 currentClocks = this.remainingClocks;
             }
             int maxClocks = (int) (this.cpuCyclesTotal - this.emulatorTicks) << this.doubleSpeedShifter;
             if (currentClocks >= GBEMU_0) {
                 if (currentClocks <= maxClocks) {
                     this.cpuTicks = Math.max(currentClocks, this.cpuTicks);
                     this.updateCoreFull();
                     this.halt = false;
                     this.cpuTicks = GBEMU_0;
                 } else {
                     this.cpuTicks = Math.max(maxClocks, this.cpuTicks);
                     this.remainingClocks = currentClocks - this.cpuTicks;
                 }
             } else {
                 this.cpuTicks += maxClocks;
             }
         }
         // Memory Reading:
         public int memoryRead(int address) {
             // Act as a wrapper for reading the returns from the compiled jumps to memory.
             return this.memoryReader.get(address).call(this, address); // This seems to be faster than the usual if/else.
         }
         public int memoryHighRead(int address) {
             // Act as a wrapper for reading the returns from the compiled jumps to memory.
             return this.memoryHighReader.get(address).call(this, address); // This seems to be faster than the usual if/else.
         }
         public void memoryReadJumpCompile() {
             debugLog("This is memoryReadJumpCompile");
             // Faster in some browsers, since we are doing less conditionals overall by implementing them in advance.
             for (int index = GBEMU_0x0000; index <= GBEMU_0xFFFF; index++) {
                 if (index < GBEMU_0x4000) {
                     this.memoryReader.set(index, GameBoyCore::memoryReadNormal);
                 } else if (index < GBEMU_0x8000) {
                     this.memoryReader.set(index, GameBoyCore::memoryReadrom);
                 } else if (index < GBEMU_0x9800) {
                     this.memoryReader.set(index, this.cGBC ? GameBoyCore::vRAMDATAReadCGBCPU : GameBoyCore::vRAMDATAReadDMGCPU);
                 } else if (index < GBEMU_0xA000) {
                     this.memoryReader.set(index, this.cGBC ? GameBoyCore::vRAMCHRReadCGBCPU : GameBoyCore::vRAMCHRReadDMGCPU);
                 } else if (index >= GBEMU_0xA000 && index < GBEMU_0xC000) {
                     if ((this.numRamBanks == 1 / GBEMU_16 && index < GBEMU_0xA200) || this.numRamBanks >= 1) {
                         if (this.cMBC7) {
                             this.memoryReader.set(index, GameBoyCore::memoryReadMBC7);
                         } else if (!this.cMBC3) {
                             this.memoryReader.set(index, GameBoyCore::memoryReadMBC);
                         } else {
                             this.memoryReader.set(index, GameBoyCore::memoryReadMBC3); // MBC3 RTC + RAM
                         }
                     } else {
                         this.memoryReader.set(index, GameBoyCore::memoryReadBAD);
                     }
                 } else if (index >= GBEMU_0xC000 && index < GBEMU_0xE000) {
                     if (!this.cGBC || index < GBEMU_0xD000) {
                         this.memoryReader.set(index, GameBoyCore::memoryReadNormal);
                     } else {
                         this.memoryReader.set(index, GameBoyCore::memoryReadgbcMemory);
                     }
                 } else if (index >= GBEMU_0xE000 && index < GBEMU_0xFE00) {
                     if (!this.cGBC || index < GBEMU_0xF000) {
                         this.memoryReader.set(index, GameBoyCore::memoryReadECHONormal);
                     } else {
                         this.memoryReader.set(index, GameBoyCore::memoryReadECHOgbcMemory);
                     }
                 } else if (index < GBEMU_0xFEA0) {
                     this.memoryReader.set(index, GameBoyCore::memoryReadOAM);
                 } else if (this.cGBC && index >= GBEMU_0xFEA0 && index < GBEMU_0xFF00) {
                     this.memoryReader.set(index, GameBoyCore::memoryReadNormal);
                 } else if (index >= GBEMU_0xFF00) {
                     switch (index) {
                         case GBEMU_0xFF00:
                             // JOYPAD:
                             this.memoryReader.set(GBEMU_0xFF00, (parentObj, address) -> {
                                 return GBEMU_0xC0 | parentObj.memory.get(GBEMU_0xFF00); // Top nibble returns as set.
                             });
                             this.memoryHighReader.set(0, this.memoryReader.get(GBEMU_0xFF00));
                             break;
                         case GBEMU_0xFF01:
                             // SB
                             this.memoryReader.set(GBEMU_0xFF01, (parentObj, address) -> {
                                 return parentObj.memory.get(GBEMU_0xFF02) < GBEMU_0x80 ? parentObj.memory.get(GBEMU_0xFF01) : GBEMU_0xFF;
                             });
                             this.memoryHighReader.set(GBEMU_0x01, this.memoryReader.get(GBEMU_0xFF01));
                             break;
                         case GBEMU_0xFF02:
                             // SC
                             if (this.cGBC) {
                                 this.memoryReader.set(GBEMU_0xFF02, (parentObj, address) -> {
                                     return (parentObj.serialTimer <= 0 ? GBEMU_0x7C : GBEMU_0xFC) | parentObj.memory.get(GBEMU_0xFF02);
                                 });
                                 this.memoryHighReader.set(GBEMU_0x02, this.memoryReader.get(GBEMU_0xFF02));
                             } else {
                                 this.memoryReader.set(GBEMU_0xFF02, (parentObj, address) -> {
                                     return (parentObj.serialTimer <= 0 ? GBEMU_0x7E : GBEMU_0xFE) | parentObj.memory.get(GBEMU_0xFF02);
                                 });
                                 this.memoryHighReader.set(GBEMU_0x02, this.memoryReader.get(GBEMU_0xFF02));
                             }
                             break;
                         case GBEMU_0xFF04:
                             // DIV
                             this.memoryReader.set(GBEMU_0xFF04, (parentObj, address) -> {
                                 parentObj.memory.set(GBEMU_0xFF04, (parentObj.memory.get(GBEMU_0xFF04) + (parentObj.divTicks >> GBEMU_8)) & GBEMU_0xFF);
                                 parentObj.divTicks &= GBEMU_0xFF;
                                 return parentObj.memory.get(GBEMU_0xFF04);
                             });
                             this.memoryHighReader.set(GBEMU_0x04, this.memoryReader.get(GBEMU_0xFF04));
                             break;
                         case GBEMU_0xFF07:
                             this.memoryReader.set(GBEMU_0xFF07, (parentObj, address) -> {
                                 return GBEMU_0xF8 | parentObj.memory.get(GBEMU_0xFF07);
                             });
                             this.memoryHighReader.set(GBEMU_0x07, this.memoryReader.get(GBEMU_0xFF07));
                             break;
                         case GBEMU_0xFF0F:
                             // IF
                             this.memoryReader.set(GBEMU_0xFF0F, (parentObj, address) -> {
                                 return GBEMU_0xE0 | parentObj.interruptsRequested;
                             });
                             this.memoryHighReader.set(GBEMU_0x0F, this.memoryReader.get(GBEMU_0xFF0F));
                             break;
                         case GBEMU_0xFF10:
                             this.memoryReader.set(GBEMU_0xFF10, (parentObj, address) -> {
                                 return GBEMU_0x80 | parentObj.memory.get(GBEMU_0xFF10);
                             });
                             this.memoryHighReader.set(GBEMU_0x10, this.memoryReader.get(GBEMU_0xFF10));
                             break;
                         case GBEMU_0xFF11:
                             this.memoryReader.set(GBEMU_0xFF11, (parentObj, address) -> {
                                 return GBEMU_0x3F | parentObj.memory.get(GBEMU_0xFF11);
                             });
                             this.memoryHighReader.set(GBEMU_0x11, this.memoryReader.get(GBEMU_0xFF11));
                             break;
                         case GBEMU_0xFF13:
                             this.memoryHighReader.set(GBEMU_0x13, GameBoyCore::memoryReadBAD);
                             this.memoryReader.set(GBEMU_0xFF13, GameBoyCore::memoryReadBAD);
                             break;
                         case GBEMU_0xFF14:
                             this.memoryReader.set(GBEMU_0xFF14, (parentObj, address) -> {
                                 return GBEMU_0xBF | parentObj.memory.get(GBEMU_0xFF14);
                             });
                             this.memoryHighReader.set(GBEMU_0x14, this.memoryReader.get(GBEMU_0xFF14));
                             break;
                         case GBEMU_0xFF16:
                             this.memoryReader.set(GBEMU_0xFF16, (parentObj, address) -> {
                                 return GBEMU_0x3F | parentObj.memory.get(GBEMU_0xFF16);
                             });
                             this.memoryHighReader.set(GBEMU_0x16, this.memoryReader.get(GBEMU_0xFF16));
                             break;
                         case GBEMU_0xFF18:
                             this.memoryHighReader.set(GBEMU_0x18, GameBoyCore::memoryReadBAD);
                             this.memoryReader.set(GBEMU_0xFF18, GameBoyCore::memoryReadBAD);
                             break;
                         case GBEMU_0xFF19:
                             this.memoryReader.set(GBEMU_0xFF19, (parentObj, address) -> {
                                 return GBEMU_0xBF | parentObj.memory.get(GBEMU_0xFF19);
                             });
                             this.memoryHighReader.set(GBEMU_0x19, this.memoryReader.get(GBEMU_0xFF19));
                             break;
                         case GBEMU_0xFF1A:
                             this.memoryReader.set(GBEMU_0xFF1A, (parentObj, address) -> {
                                 return GBEMU_0x7F | parentObj.memory.get(GBEMU_0xFF1A);
                             });
                             this.memoryHighReader.set(GBEMU_0x1A, this.memoryReader.get(GBEMU_0xFF1A));
                             break;
                         case GBEMU_0xFF1B:
                             this.memoryHighReader.set(GBEMU_0x1B, GameBoyCore::memoryReadBAD);
                             this.memoryReader.set(GBEMU_0xFF1B, GameBoyCore::memoryReadBAD);
                             break;
                         case GBEMU_0xFF1C:
                             this.memoryReader.set(GBEMU_0xFF1C, (parentObj, address) -> {
                                 return GBEMU_0x9F | parentObj.memory.get(GBEMU_0xFF1C);
                             });
                             this.memoryHighReader.set(GBEMU_0x1C, this.memoryReader.get(GBEMU_0xFF1C));
                             break;
                         case GBEMU_0xFF1D:
                             this.memoryReader.set(GBEMU_0xFF1D, (parentObj, address) -> {
                                 return GBEMU_0xFF;
                             });
                             this.memoryHighReader.set(GBEMU_0x1D, this.memoryReader.get(GBEMU_0xFF1D));
                             break;
                         case GBEMU_0xFF1E:
                             this.memoryReader.set(GBEMU_0xFF1E, (parentObj, address) -> {
                                 return GBEMU_0xBF | parentObj.memory.get(GBEMU_0xFF1E);
                             });
                             this.memoryHighReader.set(GBEMU_0x1E, this.memoryReader.get(GBEMU_0xFF1E));
                             break;
                         case GBEMU_0xFF1F:
                         case GBEMU_0xFF20:
                             this.memoryHighReader.set(index & GBEMU_0xFF, GameBoyCore::memoryReadBAD);
                             this.memoryReader.set(index, GameBoyCore::memoryReadBAD);
                             break;
                         case GBEMU_0xFF23:
                             this.memoryReader.set(GBEMU_0xFF23, (parentObj, address) -> {
                                 return GBEMU_0xBF | parentObj.memory.get(GBEMU_0xFF23);
                             });
                             this.memoryHighReader.set(GBEMU_0x23, this.memoryReader.get(GBEMU_0xFF23));
                             break;
                         case GBEMU_0xFF26:
                             this.memoryReader.set(GBEMU_0xFF26, (parentObj, address) -> {
                                 parentObj.audioJIT();
                                 return GBEMU_0x70 | parentObj.memory.get(GBEMU_0xFF26);
                             });
                             this.memoryHighReader.set(GBEMU_0x26, this.memoryReader.get(GBEMU_0xFF26));
                             break;
                         case GBEMU_0xFF27:
                         case GBEMU_0xFF28:
                         case GBEMU_0xFF29:
                         case GBEMU_0xFF2A:
                         case GBEMU_0xFF2B:
                         case GBEMU_0xFF2C:
                         case GBEMU_0xFF2D:
                         case GBEMU_0xFF2E:
                         case GBEMU_0xFF2F:
                             this.memoryReader.set(index, GameBoyCore::memoryReadBAD);
                             this.memoryHighReader.set(index & GBEMU_0xFF, this.memoryReader.get(index));
                             break;
                         case GBEMU_0xFF30:
                         case GBEMU_0xFF31:
                         case GBEMU_0xFF32:
                         case GBEMU_0xFF33:
                         case GBEMU_0xFF34:
                         case GBEMU_0xFF35:
                         case GBEMU_0xFF36:
                         case GBEMU_0xFF37:
                         case GBEMU_0xFF38:
                         case GBEMU_0xFF39:
                         case GBEMU_0xFF3A:
                         case GBEMU_0xFF3B:
                         case GBEMU_0xFF3C:
                         case GBEMU_0xFF3D:
                         case GBEMU_0xFF3E:
                         case GBEMU_0xFF3F:
                             this.memoryReader.set(index, (parentObj, address) -> {
                                 return parentObj.channel3canPlay ? parentObj.memory.get(GBEMU_0xFF00 | (parentObj.channel3lastSampleLookup >> 1)) : parentObj.memory.get(address);
                             });
                             this.memoryHighReader.set(index & GBEMU_0xFF, (parentObj, address) -> {
                                 return parentObj.channel3canPlay ?
                                         parentObj.memory.get(GBEMU_0xFF00 | (parentObj.channel3lastSampleLookup >> 1)) :
                                         parentObj.memory.get(GBEMU_0xFF00 | address);
                             });
                             break;
                         case GBEMU_0xFF41:
                             this.memoryReader.set(GBEMU_0xFF41, (parentObj, address) -> {
                                 return GBEMU_0x80 | parentObj.memory.get(GBEMU_0xFF41) | parentObj.modeSTAT;
                             });
                             this.memoryHighReader.set(GBEMU_0x41, this.memoryReader.get(GBEMU_0xFF41));
                             break;
                         case GBEMU_0xFF42:
                             this.memoryReader.set(GBEMU_0xFF42, (parentObj, address) -> {
                                 return parentObj.backgroundY;
                             });
                             this.memoryHighReader.set(GBEMU_0x42, this.memoryReader.get(GBEMU_0xFF42));
                             break;
                         case GBEMU_0xFF43:
                             this.memoryReader.set(GBEMU_0xFF43, (parentObj, address) -> {
                                 return parentObj.backgroundX;
                             });
                             this.memoryHighReader.set(GBEMU_0x43, this.memoryReader.get(GBEMU_0xFF43));
                             break;
                         case GBEMU_0xFF44:
                             this.memoryReader.set(GBEMU_0xFF44, (parentObj, address) -> {
                                 return parentObj.lcdIsOn ? parentObj.memory.get(GBEMU_0xFF44) : 0;
                             });
                             this.memoryHighReader.set(GBEMU_0x44, this.memoryReader.get(GBEMU_0xFF44));
                             break;
                         case GBEMU_0xFF4A:
                             // WY
                             this.memoryReader.set(GBEMU_0xFF4A, (parentObj, address) -> {
                                 return parentObj.windowY;
                             });
                             this.memoryHighReader.set(GBEMU_0x4A, this.memoryReader.get(GBEMU_0xFF4A));
                             break;
                         case GBEMU_0xFF4F:
                             this.memoryReader.set(GBEMU_0xFF4F, (parentObj, address) -> {
                                 return parentObj.currvramBank;
                             });
                             this.memoryHighReader.set(GBEMU_0x4F, this.memoryReader.get(GBEMU_0xFF4F));
                             break;
                         case GBEMU_0xFF55:
                             if (this.cGBC) {
                                 this.memoryReader.set(GBEMU_0xFF55, (parentObj, address) -> {
                                     if (!parentObj.lcdIsOn && parentObj.hdmaRunning) {
                                         // Undocumented behavior alert: HDMA becomes GDMA when LCD is oFF (Worms Armageddon Fix).
                                         // DMA
                                         parentObj.dMAWrite((parentObj.memory.get(GBEMU_0xFF55) & GBEMU_0x7f) + 1);
                                         parentObj.memory.set(GBEMU_0xFF55, GBEMU_0xFF); // Transfer completed.
                                         parentObj.hdmaRunning = false;
                                     }
                                     return parentObj.memory.get(GBEMU_0xFF55);
                                 });
                                 this.memoryHighReader.set(GBEMU_0x55, this.memoryReader.get(GBEMU_0xFF55));
                             } else {
                                 this.memoryReader.set(GBEMU_0xFF55, GameBoyCore::memoryReadNormal);
                                 this.memoryHighReader.set(GBEMU_0x55, GameBoyCore::memoryHighReadNormal);
                             }
                             break;
                         case GBEMU_0xFF56:
                             if (this.cGBC) {
                                 this.memoryReader.set(GBEMU_0xFF56, (parentObj, address) -> {
                                     // Return IR 'not connected' status:
                                     return (
                                             GBEMU_0x3C |
                                                     (parentObj.memory.get(GBEMU_0xFF56) >= GBEMU_0xC0 ?
                                                             GBEMU_0x2 | (parentObj.memory.get(GBEMU_0xFF56) & GBEMU_0xC1) :
                                                             parentObj.memory.get(GBEMU_0xFF56) & GBEMU_0xC3)
                                     );
                                 });
                                 this.memoryHighReader.set(GBEMU_0x56, this.memoryReader.get(GBEMU_0xFF56));
                             } else {
                                 this.memoryReader.set(GBEMU_0xFF56, GameBoyCore::memoryReadNormal);
                                 this.memoryHighReader.set(GBEMU_0x56, GameBoyCore::memoryHighReadNormal);
                             }
                             break;
                         case GBEMU_0xFF6C:
                             if (this.cGBC) {
                                 this.memoryReader.set(GBEMU_0xFF6C, (parentObj, address) -> {
                                     return GBEMU_0xFE | parentObj.memory.get(GBEMU_0xFF6C);
                                 });
                                 this.memoryHighReader.set(GBEMU_0x6c, this.memoryReader.get(GBEMU_0xFF6C));
                             } else {
                                 this.memoryReader.set(GBEMU_0xFF6C, GameBoyCore::memoryReadBAD);
                                 this.memoryHighReader.set(GBEMU_0x6C, GameBoyCore::memoryReadBAD);
                             }
                             break;
                         case GBEMU_0xFF70:
                             if (this.cGBC) {
                                 // SVBK
                                 this.memoryReader.set(GBEMU_0xFF70, (parentObj, address) -> {
                                     return GBEMU_0x40 | parentObj.memory.get(GBEMU_0xFF70);
                                 });
                                 this.memoryHighReader.set(GBEMU_0x70, this.memoryReader.get(GBEMU_0xFF70));
                             } else {
                                 this.memoryReader.set(GBEMU_0xFF70, GameBoyCore::memoryReadBAD);
                                 this.memoryHighReader.set(GBEMU_0x70, GameBoyCore::memoryReadBAD);
                             }
                             break;
                         case GBEMU_0xFF75:
                             this.memoryReader.set(GBEMU_0xFF75, (parentObj, address) -> {
                                 return GBEMU_0x8F | parentObj.memory.get(GBEMU_0xFF75);
                             });
                             this.memoryHighReader.set(GBEMU_0x75, this.memoryReader.get(GBEMU_0xFF75));
                             break;
                         case GBEMU_0xFF76:
                         case GBEMU_0xFF77:
                             this.memoryReader.set(index, (parentObj, address) -> {
                                 return 0;
                             });
                             this.memoryHighReader.set(index & GBEMU_0xFF, this.memoryReader.get(index));
                             break;
                         case GBEMU_0xFFFF:
                             // IE
                             this.memoryReader.set(GBEMU_0xFFFF, (parentObj, address) -> {
                                 return parentObj.interruptsEnabled;
                             });
                             this.memoryHighReader.set(GBEMU_0xFF, this.memoryReader.get(GBEMU_0xFFFF));
                             break;
                         default:
                             this.memoryReader.set(index, GameBoyCore::memoryReadNormal);
                             this.memoryHighReader.set(index & GBEMU_0xFF, GameBoyCore::memoryHighReadNormal);
                     }
                 } else {
                     this.memoryReader.set(index, GameBoyCore::memoryReadBAD);
                 }
             }
         }
         public static int memoryReadNormal(GameBoyCore parentObj, int address){
             return parentObj.memory.get(address);
         };
         public static int memoryHighReadNormal(GameBoyCore parentObj, int address) {
             return parentObj.memory.get(GBEMU_0xFF00 | address);
         };
         public static int memoryReadrom(GameBoyCore parentObj, int address) {
             return parentObj.rom.get(parentObj.currentromBank + address);
         };
         public static int memoryReadMBC(GameBoyCore parentObj, int address) {
             // Switchable RAM
             if (parentObj.mbcRamBanksEnabled || (boolean) settings[GBEMU_10]) {
                 return parentObj.mbcRam.get(address + parentObj.currMBCRAMBankPosition);
             }
             // cout('Reading from disabled RAM.', 1);
             return GBEMU_0xFF;
         };
         public static int memoryReadMBC7(GameBoyCore parentObj, int address) {
             debugLog("This is memoryReadMBC7");
             // Switchable RAM
             if (parentObj.mbcRamBanksEnabled || (boolean) settings[GBEMU_10]) {
                 switch (address) {
                     case GBEMU_0xA000:
                     case GBEMU_0xA060:
                     case GBEMU_0xA070:
                         return 0;
                     case GBEMU_0xA080:
                         // TODO: Gyro Control Register
                         return 0;
                     case GBEMU_0xA050:
                         // Y High Byte
                         return parentObj.highY;
                     case GBEMU_0xA040:
                         // Y Low Byte
                         return parentObj.lowY;
                     case GBEMU_0xA030:
                         // X High Byte
                         return parentObj.highX;
                     case GBEMU_0xA020:
                         // X Low Byte:
                         return parentObj.lowX;
                     default:
                         return parentObj.mbcRam.get(address + parentObj.currMBCRAMBankPosition);
                 }
             }
             // cout('Reading from disabled RAM.', 1);
             return GBEMU_0xFF;
         };
         public static int memoryReadMBC3(GameBoyCore parentObj, int address) {
             debugLog("This is memoryReadMBC3");
             // Switchable RAM
             if (parentObj.mbcRamBanksEnabled || (boolean) settings[GBEMU_10]) {
                 switch (parentObj.currMBCRAMBank) {
                     case GBEMU_0x00:
                     case GBEMU_0x01:
                     case GBEMU_0x02:
                     case GBEMU_0x03:
                         return parentObj.mbcRam.get(address + parentObj.currMBCRAMBankPosition);
                     case GBEMU_0x08:
                         return parentObj.latchedSeconds;
                     case GBEMU_0x09:
                         return parentObj.latchedMinutes;
                     case GBEMU_0x0A:
                         return parentObj.latchedHours;
                     case GBEMU_0x0B:
                         return parentObj.latchedLDays;
                     case GBEMU_0x0C:
                         return (parentObj.rtcDayOverFlow ? GBEMU_0x80 : 0) + (parentObj.rtcHalt ? GBEMU_0x40 : 0) + parentObj.latchedHDays;
                     default:
                         return 0;
                 }
             }
             // cout('Reading from invalid or disabled RAM.', 1);
             return GBEMU_0xFF;
         };
         public static int memoryReadgbcMemory(GameBoyCore parentObj, int address) {
             return parentObj.gbcMemory.get(address + parentObj.gbcRamBankPosition);
         };
         public static int memoryReadOAM(GameBoyCore parentObj, int address) {
             return parentObj.modeSTAT > 1 ? GBEMU_0xFF : parentObj.memory.get(address);
         };
         public static int memoryReadECHOgbcMemory(GameBoyCore parentObj, int address) {
             return parentObj.gbcMemory.get(address + parentObj.gbcRamBankPositionECHO);
         };
         public static int memoryReadECHONormal(GameBoyCore parentObj, int address) {
             return parentObj.memory.get(address - GBEMU_0x2000);
         };
         public static int memoryReadBAD(GameBoyCore parentObj, int address) {
             return GBEMU_0xFF;
         };
         public static int vRAMDATAReadCGBCPU(GameBoyCore parentObj, int address) {
             // CPU Side Reading The vram (Optimized for GameBoy Color)
             return parentObj.modeSTAT > GBEMU_2 ? GBEMU_0xFF : parentObj.currvramBank == 0 ? parentObj.memory.get(address) : parentObj.vram.get(address & GBEMU_0x1fff);
         };
         public static int vRAMDATAReadDMGCPU(GameBoyCore parentObj, int address) {
             // CPU Side Reading The vram (Optimized for classic GameBoy)
             return parentObj.modeSTAT > GBEMU_2 ? GBEMU_0xFF : parentObj.memory.get(address);
         };
         public static int vRAMCHRReadCGBCPU(GameBoyCore parentObj, int address) {
             // CPU Side Reading the Character Data Map:
             return parentObj.modeSTAT > GBEMU_2 ? GBEMU_0xFF : parentObj.bgCHRCurrentBank.array.get(address & GBEMU_0x7FF);
         };
         public static int vRAMCHRReadDMGCPU(GameBoyCore parentObj, int address) {
             // CPU Side Reading the Character Data Map:
             return parentObj.modeSTAT > GBEMU_2 ? GBEMU_0xFF : parentObj.bgCHRBank1.array.get(address & GBEMU_0x7FF);
         };
         public void setCurrentMBC1romBank() {
             debugLog("This is setCurrentMBC1romBank");
             // Read the cartridge rom data from RAM memory:
             switch (this.romBank1offs) {
                 case GBEMU_0x00:
                 case GBEMU_0x20:
                 case GBEMU_0x40:
                 case GBEMU_0x60:
                     // Bank calls for 0x00, 0x20, 0x40, and 0x60 are really for 0x01, 0x21, 0x41, and 0x61.
                     this.currentromBank = this.romBank1offs % this.romBankEdge << GBEMU_14;
                     break;
                 default:
                     this.currentromBank = ((this.romBank1offs % this.romBankEdge) - 1) << GBEMU_14;
             }
         }
         public void setCurrentMBC2AND3romBank() {
             // Read the cartridge rom data from RAM memory:
             // Only map bank 0 to bank 1 here (MBC2 is like MBC1, but can only do GBEMU_16 banks, so only the bank 0 quirk appears for MBC2):
             this.currentromBank = Math.max((this.romBank1offs % this.romBankEdge) - 1, 0) << GBEMU_14;
         }
         public void setCurrentMBC5romBank() {
             // Read the cartridge rom data from RAM memory:
             this.currentromBank = ((this.romBank1offs % this.romBankEdge) - 1) << GBEMU_14;
         }
         //Memory Writing:
         public void memoryWrite(int address, int data) {
             // Act as a wrapper for writing by compiled jumps to specific memory writing functions.
             this.memoryWriter.get(address).call(this, address, data);
         }
         // 0xFFXX fast path:
         public void memoryHighWrite(int address, int data) {
             // Act as a wrapper for writing by compiled jumps to specific memory writing functions.
             this.memoryHighWriter.get(address).call(this, address, data);
         }
         public void memoryWriteJumpCompile() {
             debugLog("This is memoryWriteJumpCompile");
             // Faster in some browsers, since we are doing less conditionals overall by implementing them in advance.
             for (int index = GBEMU_0x0000; index <= GBEMU_0xFFFF; index++) {
                 if (index < GBEMU_0x8000) {
                     if (this.cMBC1) {
                         if (index < GBEMU_0x2000) {
                             this.memoryWriter.set(index, GameBoyCore::mBCWriteEnable);
                         } else if (index < GBEMU_0x4000) {
                             this.memoryWriter.set(index, GameBoyCore::mBC1WriteromBank);
                         } else if (index < GBEMU_0x6000) {
                             this.memoryWriter.set(index, GameBoyCore::mBC1WriteRAMBank);
                         } else {
                             this.memoryWriter.set(index, GameBoyCore::mBC1WriteType);
                         }
                     } else if (this.cMBC2) {
                         if (index < GBEMU_0x1000) {
                             this.memoryWriter.set(index, GameBoyCore::mBCWriteEnable);
                         } else if (index >= GBEMU_0x2100 && index < GBEMU_0x2200) {
                             this.memoryWriter.set(index, GameBoyCore::mBC2WriteromBank);
                         } else {
                             this.memoryWriter.set(index, GameBoyCore::cartIgnoreWrite);
                         }
                     } else if (this.cMBC3) {
                         if (index < GBEMU_0x2000) {
                             this.memoryWriter.set(index, GameBoyCore::mBCWriteEnable);
                         } else if (index < GBEMU_0x4000) {
                             this.memoryWriter.set(index, GameBoyCore::mBC3WriteromBank);
                         } else if (index < GBEMU_0x6000) {
                             this.memoryWriter.set(index, GameBoyCore::mBC3WriteRAMBank);
                         } else {
                             this.memoryWriter.set(index, GameBoyCore::mBC3WriteRTCLatch);
                         }
                     } else if (this.cMBC5 || this.cRUMBLE || this.cMBC7) {
                         if (index < GBEMU_0x2000) {
                             this.memoryWriter.set(index, GameBoyCore::mBCWriteEnable);
                         } else if (index < GBEMU_0x3000) {
                             this.memoryWriter.set(index, GameBoyCore::mBC5WriteromBankLow);
                         } else if (index < GBEMU_0x4000) {
                             this.memoryWriter.set(index, GameBoyCore::mBC5WriteromBankHigh);
                         } else if (index < GBEMU_0x6000) {
                             this.memoryWriter.set(index, this.cRUMBLE ? GameBoyCore::rUMBLEWriteRAMBank : GameBoyCore::mBC5WriteRAMBank);
                         } else {
                             this.memoryWriter.set(index, GameBoyCore::cartIgnoreWrite);
                         }
                     } else if (this.cHuC3) {
                         if (index < GBEMU_0x2000) {
                             this.memoryWriter.set(index, GameBoyCore::mBCWriteEnable);
                         } else if (index < GBEMU_0x4000) {
                             this.memoryWriter.set(index, GameBoyCore::mBC3WriteromBank);
                         } else if (index < GBEMU_0x6000) {
                             this.memoryWriter.set(index, GameBoyCore::huC3WriteRAMBank);
                         } else {
                             this.memoryWriter.set(index, GameBoyCore::cartIgnoreWrite);
                         }
                     } else {
                         this.memoryWriter.set(index, GameBoyCore::cartIgnoreWrite);
                     }
                 } else if (index < GBEMU_0x9000) {
                     this.memoryWriter.set(index, this.cGBC ? GameBoyCore::vRAMGBCDATAWrite : GameBoyCore::vRAMGBDATAWrite);
                 } else if (index < GBEMU_0x9800) {
                     this.memoryWriter.set(index, this.cGBC ? GameBoyCore::vRAMGBCDATAWrite : GameBoyCore::vRAMGBDATAUpperWrite);
                 } else if (index < GBEMU_0xA000) {
                     this.memoryWriter.set(index, this.cGBC ? GameBoyCore::vRAMGBCCHRMAPWrite : GameBoyCore::vRAMGBCHRMAPWrite);
                 } else if (index < GBEMU_0xC000) {
                     if ((this.numRamBanks == 1 / GBEMU_16 && index < GBEMU_0xA200) || this.numRamBanks >= 1) {
                         if (!this.cMBC3) {
                             this.memoryWriter.set(index, GameBoyCore::memoryWriteMBCRAM);
                         } else {
                             this.memoryWriter.set(index, GameBoyCore::memoryWriteMBC3RAM); // MBC3 RTC + RAM
                         }
                     } else {
                         this.memoryWriter.set(index, GameBoyCore::cartIgnoreWrite);
                     }
                 } else if (index < GBEMU_0xE000) {
                     if (this.cGBC && index >= GBEMU_0xD000) {
                         this.memoryWriter.set(index, GameBoyCore::memoryWriteGBCRAM);
                     } else {
                         this.memoryWriter.set(index, GameBoyCore::memoryWriteNormal);
                     }
                 } else if (index < GBEMU_0xFE00) {
                     if (this.cGBC && index >= GBEMU_0xF000) {
                         this.memoryWriter.set(index, GameBoyCore::memoryWriteECHOGBCRAM);
                     } else {
                         this.memoryWriter.set(index, GameBoyCore::memoryWriteECHONormal);
                     }
                 } else if (index <= GBEMU_0xFEA0) {
                     this.memoryWriter.set(index, GameBoyCore::memoryWriteOAMRAM);
                 } else if (index < GBEMU_0xFF00) {
                     if (this.cGBC) {
                         // Only GBC has access to this RAM.
                         this.memoryWriter.set(index, GameBoyCore::memoryWriteNormal);
                     } else {
                         this.memoryWriter.set(index, GameBoyCore::cartIgnoreWrite);
                     }
                 } else {
                     this.memoryWriter.set(index, GameBoyCore::memoryWriteNormal);
                     this.memoryHighWriter.set(index & GBEMU_0xFF, GameBoyCore::memoryHighWriteNormal);
                 }
             }
             this.registerWriteJumpCompile(); // Compile the I/O write functions separately...
         }
         public static void mBCWriteEnable(GameBoyCore parentObj, int address, int data) {
             debugLog("This is MBCWriteEnable");
             // MBC RAM Bank Enable/Disable:
             parentObj.mbcRamBanksEnabled = (data & GBEMU_0x0F) == GBEMU_0x0A; // If lower nibble is GBEMU_0x0A, then enable, otherwise disable.
         };
         public static void mBC1WriteromBank(GameBoyCore parentObj, int address, int data) {
             debugLog("This is MBC1WriteromBank");
             // MBC1 rom bank switching:
             parentObj.romBank1offs = (parentObj.romBank1offs & GBEMU_0x60) | (data & GBEMU_0x1F);
             parentObj.setCurrentMBC1romBank();
         };
         public static void mBC1WriteRAMBank(GameBoyCore parentObj, int address, int data){
             // MBC1 RAM bank switching
             if (parentObj.mbc1Mode) {
                 // GBEMU_4/GBEMU_32 Mode
                 parentObj.currMBCRAMBank = data & GBEMU_0x03;
                 parentObj.currMBCRAMBankPosition = (parentObj.currMBCRAMBank << GBEMU_13) - GBEMU_0xA000;
             } else {
                 // GBEMU_16/GBEMU_8 Mode
                 parentObj.romBank1offs = ((data & GBEMU_0x03) << GBEMU_5) | (parentObj.romBank1offs & GBEMU_0x1F);
                 parentObj.setCurrentMBC1romBank();
             }
         };
         public static void mBC1WriteType(GameBoyCore parentObj, int address, int data) {
             // MBC1 mode setting:
             parentObj.mbc1Mode = (data & GBEMU_0x1) == GBEMU_0x1;
             if (parentObj.mbc1Mode) {
                 parentObj.romBank1offs &= GBEMU_0x1F;
                 parentObj.setCurrentMBC1romBank();
             } else {
                 parentObj.currMBCRAMBank = 0;
                 parentObj.currMBCRAMBankPosition = -GBEMU_0xA000;
             }
         };
         public static void mBC2WriteromBank(GameBoyCore parentObj, int address, int data) {
             // MBC2 rom bank switching:
             parentObj.romBank1offs = data & GBEMU_0x0F;
             parentObj.setCurrentMBC2AND3romBank();
         };
         public static void mBC3WriteromBank(GameBoyCore parentObj, int address, int data) {
             // MBC3 rom bank switching:
             parentObj.romBank1offs = data & GBEMU_0x7F;
             parentObj.setCurrentMBC2AND3romBank();
         };
         public static void mBC3WriteRAMBank(GameBoyCore parentObj, int address, int data) {
             parentObj.currMBCRAMBank = data;
             if (data < GBEMU_4) {
                 // MBC3 RAM bank switching
                 parentObj.currMBCRAMBankPosition = (parentObj.currMBCRAMBank << GBEMU_13) - GBEMU_0xA000;
             }
         };
         public static void mBC3WriteRTCLatch(GameBoyCore parentObj, int address, int data) {
             if (data == 0) {
                 parentObj.rtcIsLatched = false;
             } else if (!parentObj.rtcIsLatched) {
                 // Copy over the current RTC time for reading.
                 parentObj.rtcIsLatched = true;
                 parentObj.latchedSeconds = parentObj.rtcSeconds | GBEMU_0;
                 parentObj.latchedMinutes = parentObj.rtcMinutes;
                 parentObj.latchedHours = parentObj.rtcHours;
                 parentObj.latchedLDays = parentObj.rtcDays & GBEMU_0xFF;
                 parentObj.latchedHDays = parentObj.rtcDays >> GBEMU_8;
             }
         };
         public static void mBC5WriteromBankLow(GameBoyCore parentObj, int address, int data) {
             // MBC5 rom bank switching:
             parentObj.romBank1offs = (parentObj.romBank1offs & GBEMU_0x100) | data;
             parentObj.setCurrentMBC5romBank();
         };
         public static void mBC5WriteromBankHigh(GameBoyCore parentObj, int address, int data) {
             // MBC5 rom bank switching (by least significant bit):
             parentObj.romBank1offs = ((data & GBEMU_0x01) << GBEMU_8)| (parentObj.romBank1offs & GBEMU_0xFF);
             parentObj.setCurrentMBC5romBank();
         };
         public static void mBC5WriteRAMBank(GameBoyCore parentObj, int address, int data) {
             // MBC5 RAM bank switching
             parentObj.currMBCRAMBank = data & GBEMU_0xF;
             parentObj.currMBCRAMBankPosition = (parentObj.currMBCRAMBank << GBEMU_13) - GBEMU_0xA000;
         };
         public static void rUMBLEWriteRAMBank(GameBoyCore parentObj, int address, int data) {
             // MBC5 RAM bank switching
             // Like MBC5, but bit GBEMU_3 of the lower nibble is used for rumbling and bit GBEMU_2 is ignored.
             parentObj.currMBCRAMBank = data & GBEMU_0x03;
             parentObj.currMBCRAMBankPosition = (parentObj.currMBCRAMBank << GBEMU_13) - GBEMU_0xA000;
         };
         public static void huC3WriteRAMBank(GameBoyCore parentObj, int address, int data) {
             // HuC3 RAM bank switching
             parentObj.currMBCRAMBank = data & GBEMU_0x03;
             parentObj.currMBCRAMBankPosition = (parentObj.currMBCRAMBank << GBEMU_13) - GBEMU_0xA000;
         };
         public static void cartIgnoreWrite(GameBoyCore parentObj, int address, int data) {
             // We might have encountered illegal RAM writing or such, so just do nothing...
         };
         public static void memoryWriteNormal(GameBoyCore parentObj, int address, int data) {
             parentObj.memory.set(address, data);
         };
         public static void memoryHighWriteNormal(GameBoyCore parentObj, int address, int data) {
             parentObj.memory.set(GBEMU_0xFF00 | address, data);
         };
         public static void memoryWriteMBCRAM(GameBoyCore parentObj, int address, int data) {
             if (parentObj.mbcRamBanksEnabled || ((boolean) settings[GBEMU_10])) {
                 parentObj.mbcRam.set(address + parentObj.currMBCRAMBankPosition, data);
             }
         };
         public static void memoryWriteMBC3RAM(GameBoyCore parentObj, int address, int data) {
             debugLog("This is memoryWriteMBC3RAM");
             if (parentObj.mbcRamBanksEnabled || ((boolean) settings[GBEMU_10])) {
                 switch (parentObj.currMBCRAMBank) {
                     case GBEMU_0x00:
                     case GBEMU_0x01:
                     case GBEMU_0x02:
                     case GBEMU_0x03:
                         parentObj.mbcRam.set(address + parentObj.currMBCRAMBankPosition, data);
                         break;
                     case GBEMU_0x08:
                         if (data < GBEMU_60) {
                             parentObj.rtcSeconds = data;
                         } else {
                             cout("(Bank #" + parentObj.currMBCRAMBank + ") RTC write out of range: " + data, 1);
                         }
                         break;
                     case GBEMU_0x09:
                         if (data < GBEMU_60) {
                             parentObj.rtcMinutes = data;
                         } else {
                             cout("(Bank #" + parentObj.currMBCRAMBank + ") RTC write out of range: " + data, 1);
                         }
                         break;
                     case GBEMU_0x0A:
                         if (data < GBEMU_24) {
                             parentObj.rtcHours = data;
                         } else {
                             cout("(Bank #" + parentObj.currMBCRAMBank + ") RTC write out of range: " + data, 1);
                         }
                         break;
                     case GBEMU_0x0B:
                         parentObj.rtcDays = (data & GBEMU_0xFF) | (parentObj.rtcDays & GBEMU_0x100);
                         break;
                     case GBEMU_0x0C:
                         parentObj.rtcDayOverFlow = data > GBEMU_0x7F;
                         parentObj.rtcHalt = (data & GBEMU_0x40) == GBEMU_0x40;
                         parentObj.rtcDays = ((data & GBEMU_0x1) << GBEMU_8) | (parentObj.rtcDays & GBEMU_0xFF);
                         break;
                     default:
                         cout("Invalid MBC3 bank address selected: " + parentObj.currMBCRAMBank, 0);
                 }
             }
         };
         public static void memoryWriteGBCRAM(GameBoyCore parentObj, int address, int data) {
             parentObj.gbcMemory.set(address + parentObj.gbcRamBankPosition, data);
         };
         public static void memoryWriteOAMRAM(GameBoyCore parentObj, int address, int data) {
             if (parentObj.modeSTAT < GBEMU_2) {
                 // OAM RAM cannot be written to in mode GBEMU_2 & GBEMU_3
                 if (parentObj.memory.get(address) != data) {
                     parentObj.graphicsJIT();
                     parentObj.memory.set(address, data);
                 }
             }
         };
         public static void memoryWriteECHOGBCRAM(GameBoyCore parentObj, int address, int data) {
             parentObj.gbcMemory.set(address + parentObj.gbcRamBankPositionECHO, data);
         };
         public static void memoryWriteECHONormal(GameBoyCore parentObj, int address, int data) {
             parentObj.memory.set(address - GBEMU_0x2000, data);
         };
         public static void vRAMGBDATAWrite(GameBoyCore parentObj, int address, int data) {
             if (parentObj.modeSTAT < GBEMU_3) {
                 // vram cannot be written to during mode GBEMU_3
                 if (parentObj.memory.get(address) != data) {
                     // JIT the graphics render queue:
                     parentObj.graphicsJIT();
                     parentObj.memory.set(address, data);
                     parentObj.generateGBOAMTileLine(address);
                 }
             }
         };
         public static void vRAMGBDATAUpperWrite(GameBoyCore parentObj, int address, int data) {
             if (parentObj.modeSTAT < GBEMU_3) {
                 // vram cannot be written to during mode GBEMU_3
                 if (parentObj.memory.get(address) != data) {
                     // JIT the graphics render queue:
                     parentObj.graphicsJIT();
                     parentObj.memory.set(address, data);
                     parentObj.generateGBTileLine(address);
                 }
             }
         };
         public static void vRAMGBCDATAWrite(GameBoyCore parentObj, int addressTemp, int data) {
             int address = addressTemp;
             if (parentObj.modeSTAT < GBEMU_3) {
                 // vram cannot be written to during mode GBEMU_3
                 if (parentObj.currvramBank == GBEMU_0) {
                     if (parentObj.memory.get(address) != data) {
                         parentObj.graphicsJIT(); // JIT the graphics render queue
                         parentObj.memory.set(address, data);
                         parentObj.generateGBCTileLineBank1(address);
                     }
                 } else {
                     address &= GBEMU_0x1FFF;
                     if (parentObj.vram.get(address) != data) {
                         // JIT the graphics render queue:
                         parentObj.graphicsJIT();
                         parentObj.vram.set(address, data);
                         parentObj.generateGBCTileLineBank2(address);
                     }
                 }
             }
         };
         public static void vRAMGBCHRMAPWrite(GameBoyCore parentObj, int addressTemp, int data) {
             int address = addressTemp;
             if (parentObj.modeSTAT < GBEMU_3) {
                 // vram cannot be written to during mode GBEMU_3
                 address &= GBEMU_0x7FF;
                 if (parentObj.bgCHRBank1.array.get(address) != data) {
                     // JIT the graphics render queue:
                     parentObj.graphicsJIT();
                     parentObj.bgCHRBank1.array.set(address, data);
                 }
             }
         };
         public static void vRAMGBCCHRMAPWrite(GameBoyCore parentObj, int tempAddress, int data) {
             int address = tempAddress;
             if (parentObj.modeSTAT < GBEMU_3) {
                 // vram cannot be written to during mode GBEMU_3
                 address &= GBEMU_0x7FF;
                 if (parentObj.bgCHRCurrentBank.array.get(address) != data) {
                     // JIT the graphics render queue:
                     parentObj.graphicsJIT();
                     parentObj.bgCHRCurrentBank.array.set(address, data);
                 }
             }
         };
         public void dMAWrite(int tilesToTransferTemp) {
             int tilesToTransfer = tilesToTransferTemp;
             if (!this.halt) {
                 // Clock the CPU for the DMA transfer (CPU is halted during the transfer):
                 this.cpuTicks += GBEMU_4 | ((tilesToTransfer << GBEMU_5) << this.doubleSpeedShifter);
             }
             // Source address of the transfer:
             int source = (this.memory.get(GBEMU_0xFF51) << GBEMU_8) | this.memory.get(GBEMU_0xFF52);
             // Destination address in the vram memory range:
             int destination = (this.memory.get(GBEMU_0xFF53) << GBEMU_8) | this.memory.get(GBEMU_0xFF54);
             // Creating some references:
             ArrayList<GbemuPartMemoryReaderOrHighReader> memoryReader = this.memoryReader;
             // JIT the graphics render queue:
             this.graphicsJIT();
             ArrayList<Integer> memory = this.memory;
             // Determining which bank we're working on so we can optimize:
             if (this.currvramBank == 0) {
                 // DMA transfer for vram bank 0:
                 do {
                     if (destination < GBEMU_0x1800) {
                         memory.set(GBEMU_0x8000 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8001 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8002 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8003 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8004 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8005 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8006 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8007 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8008 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x8009 | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x800A | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x800B | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x800C | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x800D | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x800E | destination, memoryReader.get(source).call(this, source++));
                         memory.set(GBEMU_0x800F | destination, memoryReader.get(source).call(this, source++));
                         this.generateGBCTileBank1(destination);
                         destination += GBEMU_0x10;
                     } else {
                         destination &= GBEMU_0x7F0;
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank1.array.set(destination++, memoryReader.get(source).call(this, source++));
                         destination = (destination + GBEMU_0x1800) & GBEMU_0x1FF0;
                     }
                     source &= GBEMU_0xFFF0;
                     tilesToTransfer -= 1;
                 } while (tilesToTransfer > 0);
             } else {
                 ArrayList<Integer> vram = this.vram;
                 // DMA transfer for vram bank 1:
                 do {
                     if (destination < GBEMU_0x1800) {
                         vram.set(destination, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x1, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x2, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x3, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x4, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x5, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x6, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x7, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x8, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0x9, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0xA, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0xB, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0xC, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0xD, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0xE, memoryReader.get(source).call(this, source++));
                         vram.set(destination | GBEMU_0xF, memoryReader.get(source).call(this, source++));
                         this.generateGBCTileBank2(destination);
                         destination += GBEMU_0x10;
                     } else {
                         destination &= GBEMU_0x7F0;
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         this.bgCHRBank2.array.set(destination++, memoryReader.get(source).call(this, source++));
                         destination = (destination + GBEMU_0x1800) & GBEMU_0x1FF0;
                     }
                     source &= GBEMU_0xFFF0;
                     tilesToTransfer -= 1;
                 } while (tilesToTransfer > 0);
             }
             // Update the HDMA registers to their next addresses:
             memory.set(GBEMU_0xFF51, source >> GBEMU_8);
             memory.set(GBEMU_0xFF52, source & GBEMU_0xF0);
             memory.set(GBEMU_0xFF53, destination >> GBEMU_8);
             memory.set(GBEMU_0xFF54, destination & GBEMU_0xF0);
         }
         public void registerWriteJumpCompile() {
             debugLog("This is registerWriteJumpCompile");
             // I/O Registers (GB + GBC):
             // joyPad
             this.memoryWriter.set(GBEMU_0xFF00, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.memory.set(GBEMU_0xFF00,
                         (data & GBEMU_0x30) |
                                 (((data & GBEMU_0x20) == 0 ? parentObj.joyPad >> GBEMU_4 : GBEMU_0xF) & ((data & GBEMU_0x10) == 0 ? parentObj.joyPad & GBEMU_0xF : GBEMU_0xF)));
             });
             this.memoryHighWriter.set(0, this.memoryWriter.get(GBEMU_0xFF00));
             // SB (Serial Transfer Data)
             this.memoryWriter.set(GBEMU_0xFF01, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.memory.get(GBEMU_0xFF02) < GBEMU_0x80) {
                     // Cannot write while a serial transfer is active.
                     parentObj.memory.set(GBEMU_0xFF01, data);
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x1, this.memoryWriter.get(GBEMU_0xFF01));
             // DIV
             this.memoryWriter.set(GBEMU_0xFF04, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.divTicks &= GBEMU_0xFF; // Update DIV for realignment.
                 parentObj.memory.set(GBEMU_0xFF04, 0);
             });
             this.memoryHighWriter.set(GBEMU_0x4, this.memoryWriter.get(GBEMU_0xFF04));
             // TIMA
             this.memoryWriter.set(GBEMU_0xFF05, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.memory.set(GBEMU_0xFF05, data);
             });
             this.memoryHighWriter.set(GBEMU_0x5, this.memoryWriter.get(GBEMU_0xFF05));
             // TMA
             this.memoryWriter.set(GBEMU_0xFF06, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.memory.set(GBEMU_0xFF06, data);
             });
             this.memoryHighWriter.set(GBEMU_0x6, this.memoryWriter.get(GBEMU_0xFF06));
             // TAC
             this.memoryWriter.set(GBEMU_0xFF07, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.memory.set(GBEMU_0xFF07, data & GBEMU_0x07);
                 parentObj.timaEnabled = (data & GBEMU_0x04) == GBEMU_0x04;
                 parentObj.tacClocker = ((int) Math.pow(GBEMU_4, (data & GBEMU_0x3) != 0 ? data & GBEMU_0x3 : GBEMU_4)) << GBEMU_2; // TODO: Find a way to not make a conditional in here...
             });
             this.memoryHighWriter.set(GBEMU_0x7, this.memoryWriter.get(GBEMU_0xFF07));
             // IF (Interrupt Request)
             this.memoryWriter.set(GBEMU_0xFF0F, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.interruptsRequested = data;
                 parentObj.checkIRQMatching();
             });
             this.memoryHighWriter.set(GBEMU_0xF, this.memoryWriter.get(GBEMU_0xFF0F));
             this.memoryWriter.set(GBEMU_0xFF10, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     if (parentObj.channel1decreaseSweep && (data & GBEMU_0x08) == 0) {
                         if (parentObj.channel1numSweep != parentObj.channel1frequencySweepDivider) {
                             parentObj.channel1SweepFault = true;
                         }
                     }
                     parentObj.channel1lastTimeSweep = (data & GBEMU_0x70) >> GBEMU_4;
                     parentObj.channel1frequencySweepDivider = data & GBEMU_0x07;
                     parentObj.channel1decreaseSweep = (data & GBEMU_0x08) == GBEMU_0x08;
                     parentObj.memory.set(GBEMU_0xFF10, data);
                     parentObj.channel1EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x10, this.memoryWriter.get(GBEMU_0xFF10));
             this.memoryWriter.set(GBEMU_0xFF11, (GameBoyCore parentObj, int address, int tempData) -> {
                 int data = tempData;
                 if (parentObj.soundMasterEnabled || !parentObj.cGBC) {
                     if (parentObj.soundMasterEnabled) {
                         parentObj.audioJIT();
                     } else {
                         data &= GBEMU_0x3F;
                     }
                     parentObj.channel1CachedDuty = parentObj.dutyLookup[data >> GBEMU_6];
                     parentObj.channel1totalLength = GBEMU_0x40 - (data & GBEMU_0x3F);
                     parentObj.memory.set(GBEMU_0xFF11, data & GBEMU_0xC0);
                     parentObj.channel1EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x11, this.memoryWriter.get(GBEMU_0xFF11));
             this.memoryWriter.set(GBEMU_0xFF12, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     if (parentObj.channel1Enabled && parentObj.channel1envelopeSweeps == 0) {
                         // Zombie Volume PAPU Bug:
                         if (((parentObj.memory.get(GBEMU_0xFF12) ^ data) & GBEMU_0x8) == GBEMU_0x8) {
                             if ((parentObj.memory.get(GBEMU_0xFF12) & GBEMU_0x8) == 0) {
                                 parentObj.channel1envelopeVolume += ((parentObj.memory.get(GBEMU_0xFF12) & GBEMU_0x7) == GBEMU_0x7) ?
                                         GBEMU_2 :
                                         1;
                             }
                             parentObj.channel1envelopeVolume = (GBEMU_16 - parentObj.channel1envelopeVolume) & GBEMU_0xF;
                         } else if ((parentObj.memory.get(GBEMU_0xFF12) & GBEMU_0xF) == GBEMU_0x8) {
                             parentObj.channel1envelopeVolume = (1 + parentObj.channel1envelopeVolume) & GBEMU_0xF;
                         }
                         parentObj.channel1OutputLevelCache();
                     }
                     parentObj.channel1envelopeType = (data & GBEMU_0x08) == GBEMU_0x08;
                     parentObj.memory.set(GBEMU_0xFF12, data);
                     parentObj.channel1VolumeEnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x12, this.memoryWriter.get(GBEMU_0xFF12));
             this.memoryWriter.set(GBEMU_0xFF13, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     parentObj.channel1frequency = (parentObj.channel1frequency & GBEMU_0x700) | data;
                     parentObj.channel1FrequencyTracker = (GBEMU_0x800 - parentObj.channel1frequency) << GBEMU_2;
                     parentObj.memory.set(GBEMU_0xFF13, data);
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x13, this.memoryWriter.get(GBEMU_0xFF13));
             this.memoryWriter.set(GBEMU_0xFF14, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     parentObj.channel1consecutive = (data & GBEMU_0x40) == GBEMU_0x0;
                     parentObj.channel1frequency = ((data & GBEMU_0x7) << GBEMU_8) | (parentObj.channel1frequency & GBEMU_0xFF);
                     parentObj.channel1FrequencyTracker = (GBEMU_0x800 - parentObj.channel1frequency) << GBEMU_2;
                     if (data > GBEMU_0x7F) {
                         // Reload GBEMU_0xFF10:
                         parentObj.channel1timeSweep = parentObj.channel1lastTimeSweep;
                         parentObj.channel1numSweep = parentObj.channel1frequencySweepDivider;
                         // Reload GBEMU_0xFF12:
                         int nr12 = parentObj.memory.get(GBEMU_0xFF12);
                         parentObj.channel1envelopeVolume = nr12 >> GBEMU_4;
                         parentObj.channel1OutputLevelCache();
                         parentObj.channel1envelopeSweepsLast = (nr12 & GBEMU_0x7) - 1;
                         if (parentObj.channel1totalLength == 0) {
                             parentObj.channel1totalLength = GBEMU_0x40;
                         }
                         if (parentObj.channel1lastTimeSweep > 0 || parentObj.channel1frequencySweepDivider > 0) {
                             parentObj.memory.set(GBEMU_0xFF26, parentObj.memory.get(GBEMU_0xFF26) | GBEMU_0x1);
                         } else {
                             parentObj.memory.set(GBEMU_0xFF26, parentObj.memory.get(GBEMU_0xFF26) & GBEMU_0xFE);
                         }
                         if ((data & GBEMU_0x40) == GBEMU_0x40) {
                             parentObj.memory.set(GBEMU_0xFF26, parentObj.memory.get(GBEMU_0xFF26) | GBEMU_0x1);
                         }
                         parentObj.channel1ShadowFrequency = parentObj.channel1frequency;
                         // Reset frequency overflow check + frequency sweep type check:
                         parentObj.channel1SweepFault = false;
                         parentObj.runAudioSweep(); // Supposed to run immediately
                     }
                     parentObj.channel1EnableCheck();
                     parentObj.memory.set(GBEMU_0xFF14, data & GBEMU_0x40);
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x14, this.memoryWriter.get(GBEMU_0xFF14));
             this.memoryWriter.set(GBEMU_0xFF16, (GameBoyCore parentObj, int address, int tempData) -> {
                 int data = tempData;
                 if (parentObj.soundMasterEnabled || !parentObj.cGBC) {
                     if (parentObj.soundMasterEnabled) {
                         parentObj.audioJIT();
                     } else {
                         data &= GBEMU_0x3F;
                     }
                     parentObj.channel2CachedDuty = parentObj.dutyLookup[data >> GBEMU_6];
                     parentObj.channel2totalLength = GBEMU_0x40 - (data & GBEMU_0x3F);
                     parentObj.memory.set(GBEMU_0xFF16, data & GBEMU_0xC0);
                     parentObj.channel2EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x16, this.memoryWriter.get(GBEMU_0xFF16));
             this.memoryWriter.set(GBEMU_0xFF17, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     if (parentObj.channel2Enabled && parentObj.channel2envelopeSweeps == 0) {
                         // Zombie Volume PAPU Bug:
                         if (((parentObj.memory.get(GBEMU_0xFF17) ^ data) & GBEMU_0x8) == GBEMU_0x8) {
                             if ((parentObj.memory.get(GBEMU_0xFF17) & GBEMU_0x8) == 0) {
                                 parentObj.channel2envelopeVolume += ((parentObj.memory.get(GBEMU_0xFF17) & GBEMU_0x7) == GBEMU_0x7) ?
                                         GBEMU_2 :
                                         1;
                             }
                             parentObj.channel2envelopeVolume = (GBEMU_16 - parentObj.channel2envelopeVolume) & GBEMU_0xF;
                         } else if ((parentObj.memory.get(GBEMU_0xFF17) & GBEMU_0xF) == GBEMU_0x8) {
                             parentObj.channel2envelopeVolume = (1 + parentObj.channel2envelopeVolume) & GBEMU_0xF;
                         }
                         parentObj.channel2OutputLevelCache();
                     }
                     parentObj.channel2envelopeType = (data & GBEMU_0x08) == GBEMU_0x08;
                     parentObj.memory.set(GBEMU_0xFF17, data);
                     parentObj.channel2VolumeEnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x17, this.memoryWriter.get(GBEMU_0xFF17));
             this.memoryWriter.set(GBEMU_0xFF18, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     parentObj.channel2frequency = (parentObj.channel2frequency & GBEMU_0x700) | data;
                     parentObj.channel2FrequencyTracker = (GBEMU_0x800 - parentObj.channel2frequency) << GBEMU_2;
                     parentObj.memory.set(GBEMU_0xFF18, data);
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x18, this.memoryWriter.get(GBEMU_0xFF18));
             this.memoryWriter.set(GBEMU_0xFF19, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     if (data > GBEMU_0x7F) {
                         // Reload GBEMU_0xFF17:
                         int nr22 = parentObj.memory.get(GBEMU_0xFF17);
                         parentObj.channel2envelopeVolume = nr22 >> GBEMU_4;
                         parentObj.channel2OutputLevelCache();
                         parentObj.channel2envelopeSweepsLast = (nr22 & GBEMU_0x7) - 1;
                         if (parentObj.channel2totalLength == 0) {
                             parentObj.channel2totalLength = GBEMU_0x40;
                         }
                         if ((data & GBEMU_0x40) == GBEMU_0x40) {
                             parentObj.memory.set(GBEMU_0xFF26, parentObj.memory.get(GBEMU_0xFF26) | GBEMU_0x2);
                         }
                     }
                     parentObj.channel2consecutive = (data & GBEMU_0x40) == GBEMU_0x0;
                     parentObj.channel2frequency = ((data & GBEMU_0x7) << GBEMU_8) | (parentObj.channel2frequency & GBEMU_0xFF);
                     parentObj.channel2FrequencyTracker = (GBEMU_0x800 - parentObj.channel2frequency) << GBEMU_2;
                     parentObj.memory.set(GBEMU_0xFF19, data & GBEMU_0x40);
                     parentObj.channel2EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x19, this.memoryWriter.get(GBEMU_0xFF19));
             this.memoryWriter.set(GBEMU_0xFF1A, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     if (!parentObj.channel3canPlay && data >= GBEMU_0x80) {
                         parentObj.channel3lastSampleLookup = 0;
                         parentObj.channel3UpdateCache();
                     }
                     parentObj.channel3canPlay = data > GBEMU_0x7F;
                     if (parentObj.channel3canPlay && parentObj.memory.get(GBEMU_0xFF1A) > GBEMU_0x7F && !parentObj.channel3consecutive) {
                         parentObj.memory.set(GBEMU_0xFF26, parentObj.memory.get(GBEMU_0xFF26) | GBEMU_0x4);
                     }
                     parentObj.memory.set(GBEMU_0xFF1A, data & GBEMU_0x80);
                     // parentObj.channel3EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x1A, this.memoryWriter.get(GBEMU_0xFF1A));
             this.memoryWriter.set(GBEMU_0xFF1B, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled || !parentObj.cGBC) {
                     if (parentObj.soundMasterEnabled) {
                         parentObj.audioJIT();
                     }
                     parentObj.channel3totalLength = GBEMU_0x100 - data;
                     parentObj.memory.set(GBEMU_0xFF1B, data);
                     parentObj.channel3EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x1B, this.memoryWriter.get(GBEMU_0xFF1B));
             this.memoryWriter.set(GBEMU_0xFF1C, (GameBoyCore parentObj, int address, int tempData) -> {
                 int data = tempData;
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     data &= GBEMU_0x60;
                     parentObj.memory.set(GBEMU_0xFF1C, data);
                     parentObj.channel3patternType = data == 0 ? GBEMU_4 : (data >> GBEMU_5) - 1;
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x1C, this.memoryWriter.get(GBEMU_0xFF1C));
             this.memoryWriter.set(GBEMU_0xFF1D, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     parentObj.channel3frequency = (parentObj.channel3frequency & GBEMU_0x700) | data;
                     parentObj.channel3FrequencyPeriod = (GBEMU_0x800 - parentObj.channel3frequency) << 1;
                     parentObj.memory.set(GBEMU_0xFF1D, data);
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x1D, this.memoryWriter.get(GBEMU_0xFF1D));
             this.memoryWriter.set(GBEMU_0xFF1E, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     if (data > GBEMU_0x7F) {
                         if (parentObj.channel3totalLength == 0) {
                             parentObj.channel3totalLength = GBEMU_0x100;
                         }
                         parentObj.channel3lastSampleLookup = 0;
                         if ((data & GBEMU_0x40) == GBEMU_0x40) {
                             parentObj.memory.set(GBEMU_0xFF26, parentObj.memory.get(GBEMU_0xFF26) | GBEMU_0x4);
                         }
                     }
                     parentObj.channel3consecutive = (data & GBEMU_0x40) == GBEMU_0x0;
                     parentObj.channel3frequency = ((data & GBEMU_0x7) << GBEMU_8) | (parentObj.channel3frequency & GBEMU_0xFF);
                     parentObj.channel3FrequencyPeriod = (GBEMU_0x800 - parentObj.channel3frequency) << 1;
                     parentObj.memory.set(GBEMU_0xFF1E, data & GBEMU_0x40);
                     parentObj.channel3EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x1E, this.memoryWriter.get(GBEMU_0xFF1E));
             this.memoryWriter.set(GBEMU_0xFF20, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled || !parentObj.cGBC) {
                     if (parentObj.soundMasterEnabled) {
                         parentObj.audioJIT();
                     }
                     parentObj.channel4totalLength = GBEMU_0x40 - (data & GBEMU_0x3F);
                     parentObj.memory.set(GBEMU_0xFF20, data | GBEMU_0xC0);
                     parentObj.channel4EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x20, this.memoryWriter.get(GBEMU_0xFF20));
             this.memoryWriter.set(GBEMU_0xFF21, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     if (parentObj.channel4Enabled && parentObj.channel4envelopeSweeps == 0) {
                         // Zombie Volume PAPU Bug:
                         if (((parentObj.memory.get(GBEMU_0xFF21) ^ data) & GBEMU_0x8) == GBEMU_0x8) {
                             if ((parentObj.memory.get(GBEMU_0xFF21) & GBEMU_0x8) == 0) {
                                 parentObj.channel4envelopeVolume += ((parentObj.memory.get(GBEMU_0xFF21) & GBEMU_0x7) == GBEMU_0x7) ?
                                         GBEMU_2 :
                                         1;
                             }
                             parentObj.channel4envelopeVolume = (GBEMU_16 - parentObj.channel4envelopeVolume) & GBEMU_0xF;
                         } else if ((parentObj.memory.get(GBEMU_0xFF21) & GBEMU_0xF) == GBEMU_0x8) {
                             parentObj.channel4envelopeVolume = (1 + parentObj.channel4envelopeVolume) & GBEMU_0xF;
                         }
                         parentObj.channel4currentVolume = parentObj.channel4envelopeVolume << parentObj.channel4VolumeShifter;
                     }
                     parentObj.channel4envelopeType = (data & GBEMU_0x08) == GBEMU_0x08;
                     parentObj.memory.set(GBEMU_0xFF21, data);
                     parentObj.channel4UpdateCache();
                     parentObj.channel4VolumeEnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x21, this.memoryWriter.get(GBEMU_0xFF21));
             this.memoryWriter.set(GBEMU_0xFF22, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     parentObj.channel4FrequencyPeriod = Math.max((data & GBEMU_0x7) << GBEMU_4, GBEMU_8) << (data >> GBEMU_4);
                     int bitWidth = data & GBEMU_0x8;
                     if ((bitWidth == GBEMU_0x8 && parentObj.channel4BitRange == GBEMU_0x7FFF) || (bitWidth == 0 && parentObj.channel4BitRange == GBEMU_0x7F)) {
                         parentObj.channel4lastSampleLookup = 0;
                         parentObj.channel4BitRange = bitWidth == GBEMU_0x8 ? GBEMU_0x7F : GBEMU_0x7FFF;
                         parentObj.channel4VolumeShifter = bitWidth == GBEMU_0x8 ? GBEMU_7 : GBEMU_15;
                         parentObj.channel4currentVolume = parentObj.channel4envelopeVolume << parentObj.channel4VolumeShifter;
                         parentObj.noiseSampleTable = bitWidth == GBEMU_0x8 ? parentObj.lsfr7Table : parentObj.lsfr15Table;
                     }
                     parentObj.memory.set(GBEMU_0xFF22, data);
                     parentObj.channel4UpdateCache();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x22, this.memoryWriter.get(GBEMU_0xFF22));
             this.memoryWriter.set(GBEMU_0xFF23, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled) {
                     parentObj.audioJIT();
                     parentObj.memory.set(GBEMU_0xFF23, data);
                     parentObj.channel4consecutive = (data & GBEMU_0x40) == GBEMU_0x0;
                     if (data > GBEMU_0x7F) {
                         int nr42 = parentObj.memory.get(GBEMU_0xFF21);
                         parentObj.channel4envelopeVolume = nr42 >> GBEMU_4;
                         parentObj.channel4currentVolume = parentObj.channel4envelopeVolume << parentObj.channel4VolumeShifter;
                         parentObj.channel4envelopeSweepsLast = (nr42 & GBEMU_0x7) - 1;
                         if (parentObj.channel4totalLength == 0) {
                             parentObj.channel4totalLength = GBEMU_0x40;
                         }
                         if ((data & GBEMU_0x40) == GBEMU_0x40) {
                             parentObj.memory.set(GBEMU_0xFF26, parentObj.memory.get(GBEMU_0xFF26) | GBEMU_0x8);
                         }
                     }
                     parentObj.channel4EnableCheck();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x23, this.memoryWriter.get(GBEMU_0xFF23));
             this.memoryWriter.set(GBEMU_0xFF24, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled && parentObj.memory.get(GBEMU_0xFF24) != data) {
                     parentObj.audioJIT();
                     parentObj.memory.set(GBEMU_0xFF24, data);
                     parentObj.vinLeftChannelMasterVolume = ((data >> GBEMU_4) & GBEMU_0x07) + 1;
                     parentObj.vinRightChannelMasterVolume = (data & GBEMU_0x07) + 1;
                     parentObj.mixerOutputLevelCache();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x24, this.memoryWriter.get(GBEMU_0xFF24));
             this.memoryWriter.set(GBEMU_0xFF25, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.soundMasterEnabled && parentObj.memory.get(GBEMU_0xFF25) != data) {
                     parentObj.audioJIT();
                     parentObj.memory.set(GBEMU_0xFF25, data);
                     parentObj.rightChannel1 = (data & GBEMU_0x01) == GBEMU_0x01;
                     parentObj.rightChannel2 = (data & GBEMU_0x02) == GBEMU_0x02;
                     parentObj.rightChannel3 = (data & GBEMU_0x04) == GBEMU_0x04;
                     parentObj.rightChannel4 = (data & GBEMU_0x08) == GBEMU_0x08;
                     parentObj.leftChannel1 = (data & GBEMU_0x10) == GBEMU_0x10;
                     parentObj.leftChannel2 = (data & GBEMU_0x20) == GBEMU_0x20;
                     parentObj.leftChannel3 = (data & GBEMU_0x40) == GBEMU_0x40;
                     parentObj.leftChannel4 = data > GBEMU_0x7F;
                     parentObj.channel1OutputLevelCache();
                     parentObj.channel2OutputLevelCache();
                     parentObj.channel3OutputLevelCache();
                     parentObj.channel4OutputLevelCache();
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x25, this.memoryWriter.get(GBEMU_0xFF25));
             this.memoryWriter.set(GBEMU_0xFF26, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.audioJIT();
                 if (!parentObj.soundMasterEnabled && data > GBEMU_0x7F) {
                     parentObj.memory.set(GBEMU_0xFF26, GBEMU_0x80);
                     parentObj.soundMasterEnabled = true;
                     parentObj.initializeAudioStartState();
                 } else if (parentObj.soundMasterEnabled && data < GBEMU_0x80) {
                     parentObj.memory.set(GBEMU_0xFF26, 0);
                     parentObj.soundMasterEnabled = false;
                     // GBDev wiki says the registers are written with zeros on power off:
                     for (int index = GBEMU_0xFF10; index < GBEMU_0xFF26; index++) {
                         parentObj.memoryWriter.get(index).call(parentObj, index, 0);
                     }
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x26, this.memoryWriter.get(GBEMU_0xFF26));
             // GBEMU_0xFF27 to GBEMU_0xFF2F don't do anything...
             this.memoryHighWriter.set(GBEMU_0x27, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF27, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x28, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF28, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x29, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF29, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x2A, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF2A, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x2B, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF2B, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x2C, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF2C, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x2D, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF2D, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x2E, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF2E, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x2F, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF2F, GameBoyCore::cartIgnoreWrite);
             // WAVE PCM RAM:
             this.memoryWriter.set(GBEMU_0xFF30, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(0, data);
             });
             this.memoryHighWriter.set(GBEMU_0x30, this.memoryWriter.get(GBEMU_0xFF30));
             this.memoryWriter.set(GBEMU_0xFF31, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x1, data);
             });
             this.memoryHighWriter.set(GBEMU_0x31, this.memoryWriter.get(GBEMU_0xFF31));
             this.memoryWriter.set(GBEMU_0xFF32, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x2, data);
             });
             this.memoryHighWriter.set(GBEMU_0x32, this.memoryWriter.get(GBEMU_0xFF32));
             this.memoryWriter.set(GBEMU_0xFF33, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x3, data);
             });
             this.memoryHighWriter.set(GBEMU_0x33, this.memoryWriter.get(GBEMU_0xFF33));
             this.memoryWriter.set(GBEMU_0xFF34, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x4, data);
             });
             this.memoryHighWriter.set(GBEMU_0x34, this.memoryWriter.get(GBEMU_0xFF34));
             this.memoryWriter.set(GBEMU_0xFF35, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x5, data);
             });
             this.memoryHighWriter.set(GBEMU_0x35, this.memoryWriter.get(GBEMU_0xFF35));
             this.memoryWriter.set(GBEMU_0xFF36, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x6, data);
             });
             this.memoryHighWriter.set(GBEMU_0x36, this.memoryWriter.get(GBEMU_0xFF36));
             this.memoryWriter.set(GBEMU_0xFF37, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x7, data);
             });
             this.memoryHighWriter.set(GBEMU_0x37, this.memoryWriter.get(GBEMU_0xFF37));
             this.memoryWriter.set(GBEMU_0xFF38, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x8, data);
             });
             this.memoryHighWriter.set(GBEMU_0x38, this.memoryWriter.get(GBEMU_0xFF38));
             this.memoryWriter.set(GBEMU_0xFF39, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0x9, data);
             });
             this.memoryHighWriter.set(GBEMU_0x39, this.memoryWriter.get(GBEMU_0xFF39));
             this.memoryWriter.set(GBEMU_0xFF3A, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0xA, data);
             });
             this.memoryHighWriter.set(GBEMU_0x3A, this.memoryWriter.get(GBEMU_0xFF3A));
             this.memoryWriter.set(GBEMU_0xFF3B, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0xB, data);
             });
             this.memoryHighWriter.set(GBEMU_0x3B, this.memoryWriter.get(GBEMU_0xFF3B));
             this.memoryWriter.set(GBEMU_0xFF3C, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0xC, data);
             });
             this.memoryHighWriter.set(GBEMU_0x3C, this.memoryWriter.get(GBEMU_0xFF3C));
             this.memoryWriter.set(GBEMU_0xFF3D, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0xD, data);
             });
             this.memoryHighWriter.set(GBEMU_0x3D, this.memoryWriter.get(GBEMU_0xFF3D));
             this.memoryWriter.set(GBEMU_0xFF3E, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0xE, data);
             });
             this.memoryHighWriter.set(GBEMU_0x3E, this.memoryWriter.get(GBEMU_0xFF3E));
             this.memoryWriter.set(GBEMU_0xFF3F, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.channel3WriteRAM(GBEMU_0xF, data);
             });
             this.memoryHighWriter.set(GBEMU_0x3F, this.memoryWriter.get(GBEMU_0xFF3F));
             // SCY
             this.memoryWriter.set(GBEMU_0xFF42, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.backgroundY != data) {
                     parentObj.midScanLineJIT();
                     parentObj.backgroundY = data;
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x42, this.memoryWriter.get(GBEMU_0xFF42));
             // SCX
             this.memoryWriter.set(GBEMU_0xFF43, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.backgroundX != data) {
                     parentObj.midScanLineJIT();
                     parentObj.backgroundX = data;
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x43, this.memoryWriter.get(GBEMU_0xFF43));
             // LY
             this.memoryWriter.set(GBEMU_0xFF44, (GameBoyCore parentObj, int address, int data) -> {
                 // Read Only:
                 if (parentObj.lcdIsOn) {
                     // Gambatte says to do this:
                     parentObj.modeSTAT = GBEMU_2;
                     parentObj.midScanlineOffset = -1;
                     parentObj.totalLinesPassed = 0;
                     parentObj.currentX = 0;
                     parentObj.queuedScanLines = 0;
                     parentObj.lastUnrenderedLine = 0;
                     parentObj.lcdTicks = 0;
                     parentObj.statTracker = 0;
                     parentObj.actualScanLine = 0;
                     parentObj.memory.set(GBEMU_0xFF44, 0);
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x44, this.memoryWriter.get(GBEMU_0xFF44));
             // LYC
             this.memoryWriter.set(GBEMU_0xFF45, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.memory.get(GBEMU_0xFF45) != data) {
                     parentObj.memory.set(GBEMU_0xFF45, data);
                     if (parentObj.lcdIsOn) {
                         parentObj.matchLYC(); // Get the compare of the first scan line.
                     }
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x45, this.memoryWriter.get(GBEMU_0xFF45));
             // WY
             this.memoryWriter.set(GBEMU_0xFF4A, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.windowY != data) {
                     parentObj.midScanLineJIT();
                     parentObj.windowY = data;
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x4A, this.memoryWriter.get(GBEMU_0xFF4A));
             // WX
             this.memoryWriter.set(GBEMU_0xFF4B, (GameBoyCore parentObj, int address, int data) -> {
                 if (parentObj.memory.get(GBEMU_0xFF4B) != data) {
                     parentObj.midScanLineJIT();
                     parentObj.memory.set(GBEMU_0xFF4B, data);
                     parentObj.windowX = data - GBEMU_7;
                 }
             });
             this.memoryHighWriter.set(GBEMU_0x4B, this.memoryWriter.get(GBEMU_0xFF4B));
             this.memoryWriter.set(GBEMU_0xFF72, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.memory.set(GBEMU_0xFF72, data);
             });
             this.memoryHighWriter.set(GBEMU_0x72, this.memoryWriter.get(GBEMU_0xFF72));
             this.memoryWriter.set(GBEMU_0xFF73, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.memory.set(GBEMU_0xFF73, data);
             });
             this.memoryHighWriter.set(GBEMU_0x73, this.memoryWriter.get(GBEMU_0xFF73));
             this.memoryWriter.set(GBEMU_0xFF75, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.memory.set(GBEMU_0xFF75, data);
             });
             this.memoryHighWriter.set(GBEMU_0x75, this.memoryWriter.get(GBEMU_0xFF75));
             this.memoryHighWriter.set(GBEMU_0x76, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF76, GameBoyCore::cartIgnoreWrite);
             this.memoryHighWriter.set(GBEMU_0x77, GameBoyCore::cartIgnoreWrite);
             this.memoryWriter.set(GBEMU_0xFF77, GameBoyCore::cartIgnoreWrite);
             // IE (Interrupt Enable)
             this.memoryWriter.set(GBEMU_0xFFFF, (GameBoyCore parentObj, int address, int data) -> {
                 parentObj.interruptsEnabled = data;
                 parentObj.checkIRQMatching();
             });
             this.memoryHighWriter.set(GBEMU_0xFF, this.memoryWriter.get(GBEMU_0xFFFF));
             this.recompileModelSpecificIOWriteHandling();
             this.recompileBootIOWriteHandling();
         }
 
         public void recompileModelSpecificIOWriteHandling() {
             debugLog("This is recompileModelSpecificIOWriteHandling");
             if (this.cGBC) {
                 //GameBoy Color Specific I/O:
                 //SC (Serial Transfer Control Register)
                 this.memoryWriter.set(GBEMU_0xFF02, (GameBoyCore parentObj, int address, int data) -> {
                     if ((data & GBEMU_0x1) == GBEMU_0x1) {
                         //Internal clock:
                         parentObj.memory.set(GBEMU_0xFF02, data & GBEMU_0x7F);
                         parentObj.serialTimer = (data & GBEMU_0x2) == 0 ? GBEMU_4096 : GBEMU_128; //Set the Serial IRQ counter.
                         parentObj.serialShiftTimer = (data & GBEMU_0x2) == 0 ? GBEMU_512 : GBEMU_16; //Set the transfer data shift counter.
                         parentObj.serialShiftTimerAllocated = parentObj.serialShiftTimer;
                     } else {
                         //External clock:
                         parentObj.memory.set(GBEMU_0xFF02, data);
                         parentObj.serialShiftTimer = 0; //Zero the timers, since we're emulating as if nothing is connected.
                         parentObj.serialShiftTimerAllocated = parentObj.serialShiftTimer;
                         parentObj.serialTimer = parentObj.serialShiftTimer;
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x2, this.memoryWriter.get(GBEMU_0xFF02));
                 this.memoryWriter.set(GBEMU_0xFF40, (GameBoyCore parentObj, int address, int data) -> {
                     if (parentObj.memory.get(GBEMU_0xFF40) != data) {
                         parentObj.midScanLineJIT();
                         boolean tempVar = data > GBEMU_0x7F;
                         if (tempVar != parentObj.lcdIsOn) {
                             //When the display mode changes...
                             parentObj.lcdIsOn = tempVar;
                             parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) & GBEMU_0x78);
                             parentObj.midScanlineOffset = -1;
                             parentObj.totalLinesPassed = 0;
                             parentObj.currentX = 0;
                             parentObj.queuedScanLines = 0;
                             parentObj.lastUnrenderedLine = 0;
                             parentObj.statTracker = 0;
                             parentObj.lcdTicks = 0;
                             parentObj.actualScanLine = 0;
                             parentObj.memory.set(GBEMU_0xFF44, 0);
                             if (parentObj.lcdIsOn) {
                                 parentObj.modeSTAT = GBEMU_2;
                                 parentObj.matchLYC(); //Get the compare of the first scan line.
                                 parentObj.lcdControl = parentObj.lineControl;
                             } else {
                                 parentObj.modeSTAT = 0;
                                 parentObj.lcdControl = parentObj.disPlayOffControl;
                                 parentObj.displayShowOff();
                             }
                             parentObj.interruptsRequested &= GBEMU_0xFD;
                         }
                         parentObj.gfxWindowCHRBankPosition = (data & GBEMU_0x40) == GBEMU_0x40 ? GBEMU_0x400 : 0;
                         parentObj.gfxWindowDisplay = (data & GBEMU_0x20) == GBEMU_0x20;
                         parentObj.gfxBackgroundBankOffset = (data & GBEMU_0x10) == GBEMU_0x10 ? 0 : GBEMU_0x80;
                         parentObj.gfxBackgroundCHRBankPosition = (data & GBEMU_0x08) == GBEMU_0x08 ? GBEMU_0x400 : 0;
                         parentObj.gfxSpriteNormalHeight = (data & GBEMU_0x04) == 0;
                         parentObj.gfxSpriteShow = (data & GBEMU_0x02) == GBEMU_0x02;
                         parentObj.bgPriorityEnabled = (data & GBEMU_0x01) == GBEMU_0x01;
                         parentObj.priorityFlaggingPathRebuild(); //Special case the priority flagging as an optimization.
                         parentObj.memory.set(GBEMU_0xFF40, data);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x40, this.memoryWriter.get(GBEMU_0xFF40));
                 this.memoryWriter.set(GBEMU_0xFF41, (GameBoyCore parentObj, int address, int data) -> {
                     parentObj.lycMatchTriggerSTAT = (data &  GBEMU_0x40) ==  GBEMU_0x40;
                     parentObj.mode2TriggerSTAT = (data &  GBEMU_0x20) ==  GBEMU_0x20;
                     parentObj.mode1TriggerSTAT = (data &  GBEMU_0x10) ==  GBEMU_0x10;
                     parentObj.mode0TriggerSTAT = (data &  GBEMU_0x08) ==  GBEMU_0x08;
                     parentObj.memory.set(GBEMU_0xFF41, data &  GBEMU_0x78);
                 });
                 this.memoryHighWriter.set(GBEMU_0x41, this.memoryWriter.get(GBEMU_0xFF41));
                 this.memoryWriter.set(GBEMU_0xFF46, (GameBoyCore parentObj, int addressTemp, int dataTemp) -> {
                     int data = dataTemp;
                     int address = addressTemp;
                     parentObj.memory.set(GBEMU_0xFF46, data);
                     if (data < GBEMU_0xE0) {
                         data <<= GBEMU_8;
                         address = GBEMU_0xFE00;
                         int stat = parentObj.modeSTAT;
                         parentObj.modeSTAT = GBEMU_0;
                         int newData = GBEMU_0;
                         do {
                             newData = parentObj.memoryReader.get(data).call(parentObj, data++);
                             if (newData != parentObj.memory.get(address)) {
                                 parentObj.modeSTAT = stat; //JIT the graphics render queue
                                 parentObj.graphicsJIT();
                                 parentObj.modeSTAT = GBEMU_0;
                                 parentObj.memory.set(address++, newData);
                                 break;
                             }
                             address += 1;
                         } while (address < GBEMU_0xFEA0);
                         if (address <  GBEMU_0xFEA0) {
                             do {
                                 parentObj.memory.set(address++, parentObj.memoryReader.get(data).call(parentObj, data++));
                                 parentObj.memory.set(address++, parentObj.memoryReader.get(data).call(parentObj, data++));
                                 parentObj.memory.set(address++, parentObj.memoryReader.get(data).call(parentObj, data++));
                                 parentObj.memory.set(address++, parentObj.memoryReader.get(data).call(parentObj, data++));
                             } while (address < GBEMU_0xFEA0);
                         }
                         parentObj.modeSTAT = stat;
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x46, this.memoryWriter.get(GBEMU_0xFF46));
                 //KEY1
                 this.memoryWriter.set(GBEMU_0xFF4D, (GameBoyCore parentObj, int address, int data) -> {
                     int temp = parentObj.memory.get(GBEMU_0xFF4D) & GBEMU_0x80;
                     parentObj.memory.set(GBEMU_0xFF4D, (data & GBEMU_0x7F) | temp);
                 });
                 this.memoryHighWriter.set(GBEMU_0x4D, this.memoryWriter.get(GBEMU_0xFF4D));
                 this.memoryWriter.set(GBEMU_0xFF4F, (GameBoyCore parentObj, int address, int data) -> {
                     parentObj.currvramBank = data & GBEMU_0x01;
                     if (parentObj.currvramBank > 0) {
                         parentObj.bgCHRCurrentBank = parentObj.bgCHRBank2;
                     } else {
                         parentObj.bgCHRCurrentBank = parentObj.bgCHRBank1;
                     }
                     //Only writable by GBC.
                 });
                 this.memoryHighWriter.set(GBEMU_0x4F, this.memoryWriter.get(GBEMU_0xFF4F));
                 this.memoryWriter.set(GBEMU_0xFF51, (GameBoyCore parentObj, int address, int data) -> {
                     if (!parentObj.hdmaRunning) {
                         parentObj.memory.set(GBEMU_0xFF51, data);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x51, this.memoryWriter.get(GBEMU_0xFF51));
                 this.memoryWriter.set(GBEMU_0xFF52, (GameBoyCore parentObj, int address, int data) -> {
                     if (!parentObj.hdmaRunning) {
                         parentObj.memory.set(GBEMU_0xFF52, data & GBEMU_0xF0);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x52, this.memoryWriter.get(GBEMU_0xFF52));
                 this.memoryWriter.set(GBEMU_0xFF53, (GameBoyCore parentObj, int address, int data) -> {
                     if (!parentObj.hdmaRunning) {
                         parentObj.memory.set(GBEMU_0xFF53, data & GBEMU_0x1F);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x53, this.memoryWriter.get(GBEMU_0xFF53));
                 this.memoryWriter.set(GBEMU_0xFF54, (GameBoyCore parentObj, int address, int data) -> {
                     if (!parentObj.hdmaRunning) {
                         parentObj.memory.set(GBEMU_0xFF54, data & GBEMU_0xF0);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x54, this.memoryWriter.get(GBEMU_0xFF54));
                 this.memoryWriter.set(GBEMU_0xFF55, (GameBoyCore parentObj, int address, int data) -> {
                     if (!parentObj.hdmaRunning) {
                         if ((data & GBEMU_0x80) == 0) {
                             //DMA
                             parentObj.dMAWrite((data & GBEMU_0x7F) + 1);
                             parentObj.memory.set(GBEMU_0xFF55, GBEMU_0xFF); //Transfer completed.
                         } else {
                             //H-Blank DMA
                             parentObj.hdmaRunning = true;
                             parentObj.memory.set(GBEMU_0xFF55, data & GBEMU_0x7F);
                         }
                     } else if ((data & GBEMU_0x80) == 0) {
                         //Stop H-Blank DMA
                         parentObj.hdmaRunning = false;
                         parentObj.memory.set(GBEMU_0xFF55, parentObj.memory.get(GBEMU_0xFF55) | GBEMU_0x80);
                     } else {
                         parentObj.memory.set(GBEMU_0xFF55, data & GBEMU_0x7F);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x55, this.memoryWriter.get(GBEMU_0xFF55));
                 this.memoryWriter.set(GBEMU_0xFF68, (GameBoyCore parentObj, int address, int data) -> {
                     parentObj.memory.set(GBEMU_0xFF69, parentObj.gbcBGRawPalette.get(data & GBEMU_0x3F));
                     parentObj.memory.set(GBEMU_0xFF68, data);
                 });
                 this.memoryHighWriter.set(GBEMU_0x68, this.memoryWriter.get(GBEMU_0xFF68));
                 this.memoryWriter.set(GBEMU_0xFF69, (GameBoyCore parentObj, int address, int data) -> {
                     parentObj.updateGBCBGPalette(parentObj.memory.get(GBEMU_0xFF68) & GBEMU_0x3F, data);
                     if (parentObj.memory.get(GBEMU_0xFF68) > GBEMU_0x7F) {
                         // high bit = autoincrement
                         int next = (parentObj.memory.get(GBEMU_0xFF68) + 1) & GBEMU_0x3F;
                         parentObj.memory.set(GBEMU_0xFF68, next | GBEMU_0x80);
                         parentObj.memory.set(GBEMU_0xFF69, parentObj.gbcBGRawPalette.get(next));
                     } else {
                         parentObj.memory.set(GBEMU_0xFF69, data);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x69, this.memoryWriter.get(GBEMU_0xFF69));
                 this.memoryWriter.set(GBEMU_0xFF6A, (GameBoyCore parentObj, int address, int data) -> {
                     parentObj.memory.set(GBEMU_0xFF6B, parentObj.gbcOBJRawPalette.get(data & GBEMU_0x3F));
                     parentObj.memory.set(GBEMU_0xFF6A, data);
                 });
                 this.memoryHighWriter.set(GBEMU_0x6A, this.memoryWriter.get(GBEMU_0xFF6A));
                 this.memoryWriter.set(GBEMU_0xFF6B, (GameBoyCore parentObj, int address, int data) -> {
                     int temp = parentObj.memory.get(GBEMU_0xFF6A);
                     parentObj.updateGBCOBJPalette(temp & GBEMU_0x3F, data);
                     if (temp > GBEMU_0x7F) {
                         // high bit = autoincrement
                         int next = (parentObj.memory.get(GBEMU_0xFF6A) + 1) & GBEMU_0x3F;
                         parentObj.memory.set(GBEMU_0xFF6A, next | GBEMU_0x80);
                         parentObj.memory.set(GBEMU_0xFF6B, parentObj.gbcOBJRawPalette.get(next));
                     } else {
                         parentObj.memory.set(GBEMU_0xFF6B, data);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x6B, this.memoryWriter.get(GBEMU_0xFF6B));
                 //SVBK
                 this.memoryWriter.set(GBEMU_0xFF70, (GameBoyCore parentObj, int address, int data) -> {
                     int addressCheck = (parentObj.memory.get(GBEMU_0xFF51) << GBEMU_8) | parentObj.memory.get(GBEMU_0xFF52); //Cannot change the RAM bank while WRAM is the source of a running HDMA.
                     if (!parentObj.hdmaRunning || addressCheck < GBEMU_0xD000 || addressCheck >= GBEMU_0xE000) {
                         parentObj.gbcRamBank = Math.max(data & GBEMU_0x07, 1); //Bank range is from 1-GBEMU_7
                         parentObj.gbcRamBankPosition = ((parentObj.gbcRamBank - 1) << GBEMU_12) - GBEMU_0xD000;
                         parentObj.gbcRamBankPositionECHO = parentObj.gbcRamBankPosition - GBEMU_0x2000;
                     }
                     parentObj.memory.set(GBEMU_0xFF70, data); //Bit GBEMU_6 cannot be written to.
                 });
                 this.memoryHighWriter.set(GBEMU_0x70, this.memoryWriter.get(GBEMU_0xFF70));
                 this.memoryWriter.set(GBEMU_0xFF74, (GameBoyCore parentObj, int address, int data) -> {
                     parentObj.memory.set(GBEMU_0xFF74, data);
                 });
                 this.memoryHighWriter.set(GBEMU_0x74, this.memoryWriter.get(GBEMU_0xFF74));
             } else {
                 //Fill in the GameBoy Color I/O registers as normal RAM for GameBoy compatibility:
                 //SC (Serial Transfer Control Register)
                 this.memoryWriter.set(GBEMU_0xFF02, (GameBoyCore parentObj, int address, int data) -> {
                     if ((data & GBEMU_0x1) == GBEMU_0x1) {
                         //Internal clock:
                         parentObj.memory.set(GBEMU_0xFF02, data & GBEMU_0x7F);
                         parentObj.serialTimer = GBEMU_4096; //Set the Serial IRQ counter.
                         parentObj.serialShiftTimer = GBEMU_512;
                         parentObj.serialShiftTimerAllocated = GBEMU_512; //Set the transfer data shift counter.
                     } else {
                         //External clock:
                         parentObj.memory.set(GBEMU_0xFF02, data);
                         parentObj.serialShiftTimer = 0;
                         parentObj.serialShiftTimerAllocated = 0;
                         parentObj.serialTimer = 0; //Zero the timers, since we're emulating as if nothing is connected.
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x2, this.memoryWriter.get(GBEMU_0xFF02));
                 this.memoryWriter.set(GBEMU_0xFF40, (GameBoyCore parentObj, int address, int data) -> {
                     if (parentObj.memory.get(GBEMU_0xFF40) != data) {
                         parentObj.midScanLineJIT();
                         boolean tempVar = data > GBEMU_0x7F;
                         if (tempVar != parentObj.lcdIsOn) {
                             //When the display mode changes...
                             parentObj.lcdIsOn = tempVar;
                             parentObj.memory.set(GBEMU_0xFF41, parentObj.memory.get(GBEMU_0xFF41) & GBEMU_0x78);
                             parentObj.midScanlineOffset = -1;
                             parentObj.totalLinesPassed = 0;
                             parentObj.currentX = 0;
                             parentObj.queuedScanLines = 0;
                             parentObj.lastUnrenderedLine = 0;
                             parentObj.statTracker = 0;
                             parentObj.lcdTicks = 0;
                             parentObj.actualScanLine = 0;
                             parentObj.memory.set(GBEMU_0xFF44, 0);
                             if (parentObj.lcdIsOn) {
                                 parentObj.modeSTAT = GBEMU_2;
                                 parentObj.matchLYC(); //Get the compare of the first scan line.
                                 parentObj.lcdControl = parentObj.lineControl;
                             } else {
                                 parentObj.modeSTAT = 0;
                                 parentObj.lcdControl = parentObj.disPlayOffControl;
                                 parentObj.displayShowOff();
                             }
                             parentObj.interruptsRequested &= 0xfd;
                         }
                         parentObj.gfxWindowCHRBankPosition = (data & GBEMU_0x40) == GBEMU_0x40 ? GBEMU_0x400 : 0;
                         parentObj.gfxWindowDisplay = (data & GBEMU_0x20) == GBEMU_0x20;
                         parentObj.gfxBackgroundBankOffset = (data & GBEMU_0x10) == GBEMU_0x10 ? 0 : GBEMU_0x80;
                         parentObj.gfxBackgroundCHRBankPosition = (data & GBEMU_0x08) == GBEMU_0x08 ? GBEMU_0x400 : 0;
                         parentObj.gfxSpriteNormalHeight = (data & GBEMU_0x04) == 0;
                         parentObj.gfxSpriteShow = (data & GBEMU_0x02) == GBEMU_0x02;
                         parentObj.bgEnabled = (data & GBEMU_0x01) == GBEMU_0x01;
                         parentObj.memory.set(GBEMU_0xFF40, data);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x40, this.memoryWriter.get(GBEMU_0xFF40));
                 this.memoryWriter.set(GBEMU_0xFF41, (GameBoyCore parentObj, int address, int data) -> {
                     parentObj.lycMatchTriggerSTAT = (data & GBEMU_0x40) == GBEMU_0x40;
                     parentObj.mode2TriggerSTAT = (data & GBEMU_0x20) == GBEMU_0x20;
                     parentObj.mode1TriggerSTAT = (data & GBEMU_0x10) == GBEMU_0x10;
                     parentObj.mode0TriggerSTAT = (data & GBEMU_0x08) == GBEMU_0x08;
                     parentObj.memory.set(GBEMU_0xFF41, data & GBEMU_0x78);
                     if ((!parentObj.usedBootrom || !parentObj.usedGBCBootrom) && parentObj.lcdIsOn && parentObj.modeSTAT < GBEMU_2) {
                         parentObj.interruptsRequested |= GBEMU_0x2;
                         parentObj.checkIRQMatching();
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x41, this.memoryWriter.get(GBEMU_0xFF41));
                 this.memoryWriter.set(GBEMU_0xFF46, (GameBoyCore parentObj, int addressTemp, int dataTemp) -> {
                     parentObj.memory.set(GBEMU_0xFF46, dataTemp);
                     int data = dataTemp;
                     int address = addressTemp;
                     if (data > GBEMU_0x7F && data < GBEMU_0xE0) {
                         //DMG cannot DMA from the rom banks.
                         data <<= GBEMU_8;
                         address = GBEMU_0xFE00;
                         int stat = parentObj.modeSTAT;
                         parentObj.modeSTAT = 0;
                         int newData = 0;
                         do {
                             newData = parentObj.memoryReader.get(data).call(parentObj, data++);
                             if (newData != parentObj.memory.get(address)) {
                                 //JIT the graphics render queue:
                                 parentObj.modeSTAT = stat;
                                 parentObj.graphicsJIT();
                                 parentObj.modeSTAT = 0;
                                 parentObj.memory.set(address++, newData);
                                 break;
                             }
                             address += 1;
                         } while (address < GBEMU_0xFEA0);
                         if (address < GBEMU_0xFEA0) {
                             do {
                                 parentObj.memory.set(address++, parentObj.memoryReader.get(data).call(parentObj, data++));
                                 parentObj.memory.set(address++, parentObj.memoryReader.get(data).call(parentObj, data++));
                                 parentObj.memory.set(address++, parentObj.memoryReader.get(data).call(parentObj, data++));
                                 parentObj.memory.set(address++, parentObj.memoryReader.get(data).call(parentObj, data++));
                             } while (address < GBEMU_0xFEA0);
                         }
                         parentObj.modeSTAT = stat;
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x46, this.memoryWriter.get(GBEMU_0xFF46));
                 this.memoryWriter.set(GBEMU_0xFF47, (GameBoyCore parentObj, int address, int data) -> {
                     if (parentObj.memory.get(GBEMU_0xFF47) != data) {
                         parentObj.midScanLineJIT();
                         parentObj.updateGBBGPalette.call(data);
                         parentObj.memory.set(GBEMU_0xFF47, data);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x47, this.memoryWriter.get(GBEMU_0xFF47));
                 this.memoryWriter.set(GBEMU_0xFF48, (GameBoyCore parentObj, int address, int data) -> {
                     if (parentObj.memory.get(GBEMU_0xFF48) != data) {
                         parentObj.midScanLineJIT();
                         parentObj.updateGBOBJPalette.call(0, data);
                         parentObj.memory.set(GBEMU_0xFF48, data);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x48, this.memoryWriter.get(GBEMU_0xFF48));
                 this.memoryWriter.set(GBEMU_0xFF49, (GameBoyCore parentObj, int address, int data) -> {
                     if (parentObj.memory.get(GBEMU_0xFF49) != data) {
                         parentObj.midScanLineJIT();
                         parentObj.updateGBOBJPalette.call(GBEMU_4, data);
                         parentObj.memory.set(GBEMU_0xFF49, data);
                     }
                 });
                 this.memoryHighWriter.set(GBEMU_0x49, this.memoryWriter.get(GBEMU_0xFF49));
                 this.memoryWriter.set(GBEMU_0xFF4D, (GameBoyCore parentObj, int address, int data) -> {
                     parentObj.memory.set(GBEMU_0xFF4D, data);
                 });
                 this.memoryHighWriter.set(GBEMU_0x4D, this.memoryWriter.get(GBEMU_0xFF4D));
                 this.memoryHighWriter.set(GBEMU_0x4F, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF4F, GameBoyCore::cartIgnoreWrite); //Not writable in DMG mode.
                 this.memoryHighWriter.set(GBEMU_0x55, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF55, GameBoyCore::cartIgnoreWrite);
                 this.memoryHighWriter.set(GBEMU_0x68, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF68, GameBoyCore::cartIgnoreWrite);
                 this.memoryHighWriter.set(GBEMU_0x69, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF69, GameBoyCore::cartIgnoreWrite);
                 this.memoryHighWriter.set(GBEMU_0x6A, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF6A, GameBoyCore::cartIgnoreWrite);
                 this.memoryHighWriter.set(GBEMU_0x6B, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF6B, GameBoyCore::cartIgnoreWrite);
                 this.memoryHighWriter.set(GBEMU_0x6C, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF6C, GameBoyCore::cartIgnoreWrite);
                 this.memoryHighWriter.set(GBEMU_0x70, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF70, GameBoyCore::cartIgnoreWrite);
                 this.memoryHighWriter.set(GBEMU_0x74, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF74, GameBoyCore::cartIgnoreWrite);
             }
         }
 
         public void recompileBootIOWriteHandling() {
             debugLog("This is recompileBootIOWriteHandling");
             //Boot I/O Registers:
             if (this.inBootstrap) {
                 this.memoryWriter.set(GBEMU_0xFF50, (GameBoyCore parentObj, int address, int data) -> {
                     debugLog("Boot rom reads blocked: Bootstrap process has ended.");
                     parentObj.inBootstrap = false;
                     parentObj.disableBootrom();
                     parentObj.memory.set(GBEMU_0xFF50, data);
                 });
                 this.memoryHighWriter.set(GBEMU_0x50, this.memoryWriter.get(GBEMU_0xFF50));
                 if (this.cGBC) {
                     this.memoryWriter.set(GBEMU_0xFF6C, (GameBoyCore parentObj, int address, int data) -> {
                         if (parentObj.inBootstrap) {
                             parentObj.cGBC = (data & GBEMU_0x1) == 0;
                             //Exception to the GBC identifying code:
                             if (parentObj.name + parentObj.gameCode + parentObj.rom.get(GBEMU_0x143) == "Game and Watch 50") {
                                 parentObj.cGBC = true;
                                 cout("Created a boot exception for Game and Watch Gallery GBEMU_2 (GBC ID byte is wrong on the cartridge).", 1);
                             }
                             cout("Booted to GBC Mode: " + parentObj.cGBC, 0);
                         }
                         parentObj.memory.set(GBEMU_0xFF6C, data);
                     });
                     this.memoryHighWriter.set(GBEMU_0x6C, this.memoryWriter.get(GBEMU_0xFF6C));
                 }
             } else {
                 //Lockout the roms from accessing the BOOT rom control register:
                 this.memoryHighWriter.set(GBEMU_0x50, GameBoyCore::cartIgnoreWrite);
                 this.memoryWriter.set(GBEMU_0xFF50, GameBoyCore::cartIgnoreWrite);
             }
         }
 
         public int[] toTypedArray(int[] baseArray, String memtype) {
             if (baseArray == null || baseArray.length == 0) {
                 return new int[0];
             }
             int length = baseArray.length;
             int[] typedArrayTemp = new int[length];
             switch (memtype) {
                 case "uint8":
                     typedArrayTemp = new int[length];
                     break;
                 case "int8":
                     typedArrayTemp = new int[length];
                     break;
                 case "int32":
                     typedArrayTemp = new int[length];
                     break;
                 case "float32":
                     typedArrayTemp = new int[length];
                 default:
                     break;
             }
             for (int index = 0; index < length; index++) {
                 typedArrayTemp[index] = baseArray[index];
             }
             return typedArrayTemp;
         }
 
         public ArrayList<Integer> fromTypedArray(ArrayList<Integer> baseArray) {
             if (baseArray == null || baseArray.size() < 0) {
                 return new ArrayList();
             }
             ArrayList<Integer> arrayTemp = new ArrayList();
             for (int index = 0; index < baseArray.size(); ++index) {
                 arrayTemp.add(baseArray.get(index));
             }
             return arrayTemp;
         }
 
         public ArrayList<Integer> getTypedArray(int length, int defaultValue, String numberType) {
             ArrayList<Integer> arrayHandle = new ArrayList<>();
             if ((boolean) settings[GBEMU_5]) {
                 for (int i = 0; i < length; i++) {
                     arrayHandle.add(defaultValue);
                 }
                 return arrayHandle;
             }
             switch (numberType) {
                 case "int8":
                     arrayHandle = new ArrayList(Collections.nCopies(length, 0));
                     break;
                 case "uint8":
                     arrayHandle = new ArrayList(Collections.nCopies(length, 0));
                     break;
                 case "int32":
                     arrayHandle = new ArrayList(Collections.nCopies(length,  0));
                     break;
                 case "float32":
                     arrayHandle = new ArrayList(Collections.nCopies(length, 0));
                 default:
                     break;
             }
             if (defaultValue != 0) {
                 int index = 0;
                 while (index < length) {
                     arrayHandle.set(index++, defaultValue);
                 }
             }
             return arrayHandle;
         }
 
         public ArrayList<Integer> toIntegetTypedArray(ArrayList<Integer> baseArray, String memtype) {
             if (baseArray == null || baseArray.size() == 0) {
                 return new ArrayList<>();
             }
             int length = baseArray.size();
             ArrayList<Integer> typedArrayTemp = new ArrayList<>(length);
             for (int index = 0; index < length; index++) {
                 typedArrayTemp.set(index, baseArray.get(index));
             }
             return typedArrayTemp;
         }
         public void initNewCanvas() {
             if (gameBoyEmulatorInitialized()) {
                 gameboy.canvas.width = gameboy.canvas.clientWidth;
                 gameboy.canvas.height = gameboy.canvas.clientHeight;
             }
         }
     }
     // End of js/GameBoyCore.js file.
 
     public static String gameboyRomFirst =
             "r+BPyZiEZwA+AeBPySAobeEq6gAgKlYj5WJv6SRmZjjhKuXqACDJ/////////////////////////////////xgHZwCYhGcA2fX6/3/1xdXlIRPKNgHN9f/h0cHx6gAg+hLKtyAC8cnwgLcoF/CC7hjgUT6Q4FOv4FLgVOCAPv/gVfHZ8IG3IALx2fBA7gjgQA8PD+YB7gHgT/CC4FHuEOCCPojgU6/gUuBU4IE+/uBV4ID6NMs86jTL8dkKCgoKbWFkZSBieSBhZ28uIGVtYWlsOmdvYnV6b3ZAeWFob28uY29tCnVybDogc3BlY2N5LmRhLnJ1CgoKCv///////wDDSgnO7WZmzA0ACwNzAIMADAANAAgRH4iJAA7czG7m3d3Zmbu7Z2NuDuzM3dyZn7u5Mz5BR08nUyBSRUFMVElNRSCAAAAAAgEDADMBSTQeIUD/y37I8P/1y4fg//BE/pEg+su+8eD/yT7A4EY+KD0g/cnF1eWvEQPK1RITEhMGAyEAyuXFTgYAIWAMCQkqEhMqEhPB4SMFIOrhrwYIzYsU4dHByf////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////8AAgMFBggJCwwOEBETFBYXGBobHR4fISIjJSYnKSorLC0uLzAxMjM0NTY3ODg5Ojo7PDw9PT4+Pj8/Pz9AQEBAQEBAQEBAPz8/Pz4+PT08PDs7Ojk5ODc2NTU0MzIxMC8uLCsqKSgmJSQjISAfHRwaGRcWFRMSEA8NCwoIBwUEAgH//fz6+ff29PPx8O7t6+ro5+Xk4uHg3t3c2tnY19bU09LR0M/OzczLysnJyMfGxsXFxMPDw8LCwcHBwcDAwMDAwMDAwMDBwcHBwsLDw8PExcXGxsfIycnKy8zNzs/Q0dLT1NXX2Nna3N3e4OHi5OXn6Onr7O7v8fL09vf5+vz9AAEECRAZJDFAUWR5kKnE4QAhRGmQueQRQHGk2RBJhMEAQYTJEFmk8UCR5DmQ6UShAGHEKZD5ZNFAsSSZEIkEgQCBBIkQmSSxQNFk+ZApxGEAoUTpkDnkkUDxpFkQyYRBAMGESRDZpHFAEeS5kGlEIQDhxKmQeWRRQDEkGRAJBAEAAQQJEBkkMUBRZHmQqcThACFEaZC55BFAcaTZEEmEwQBBhMkQWaTxQJHkOZDpRKEAYcQpkPlk0UCxJJkQiQSBAIEEiRCZJLFA0WT5kCnEYQChROmQOeSRQPGkWRDJhEEAwYRJENmkcUAR5LmQaUQhAOHEqZB5ZFFAMSQZEAkEAQAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAgICAgIDAwMDBAQEBAUFBQUGBgYHBwcICAkJCQoKCgsLDAwNDQ4ODw8QEBEREhITExQUFRUWFxcYGRkaGhscHB0eHh8gISEiIyQkJSYnJygpKisrLC0uLzAxMTIzNDU2Nzg5Ojs8PT4/QEFCQ0RFRkdISUpLTE1OT1FSU1RVVldZWltcXV9gYWJkZWZnaWprbG5vcHJzdHZ3eXp7fX5/gYKEhYeIiouNjpCRk5SWl5manJ2foKKkpaepqqytr7GytLa3ubu9vsDCxMXHycvMztDS1NXX2dvd3+Hi5Obo6uzu8PL09vj6/P4A//z38Ofcz8CvnIdwVzwfAN+8l3BHHO/Aj1wn8Ld8PwC/fDfwp1wPwG8cx3AXvF8AnzzXcAecL8BP3Gfwd/x/AH/8d/Bn3E/AL5wHcNc8nwBfvBdwxxxvwA9cp/A3fL8AP3y38Cdcj8DvHEdwl7zfAB88V3CHnK/Az9zn8Pf8/wD//Pfw59zPwK+ch3BXPB8A37yXcEcc78CPXCfwt3w/AL98N/CnXA/AbxzHcBe8XwCfPNdwB5wvwE/cZ/B3/H8Af/x38GfcT8AvnAdw1zyfAF+8F3DHHG/AD1yn8Dd8vwA/fLfwJ1yPwO8cR3CXvN8AHzxXcIecr8DP3Ofw9/z/AP/////////////////////+/v7+/v79/f39/fz8/Pz8+/v7+vr6+vn5+fj4+Pf39/b29fX19PTz8/Ly8fHw8PDv7u7t7ezs6+vq6uno6Ofn5uXl5OPj4uHh4N/e3t3c3Nva2djY19bV1NTT0tHQz8/OzczLysnIx8bFxMPCwcDAvr28u7q5uLe2tbSzsrGwr62sq6qpqKalpKOioJ+enZyamZiWlZSTkZCPjYyLiYiHhYSCgYB+fXt6eHd1dHJxcG5sa2loZmVjYmBfXVtaWFdVU1JQTk1LSUhGREJBPz08Ojg2NDMxLy0rKigmJCIgHx0bGRcVExEPDQsJBwUDAf9/Px8PBwMBgEAgEAgEAgEAAQEBAQEBAQEBAQEA//////////////+AEAcAAQABAAEBAAEBAAEA/wD//wD//wD/AP+AKwcBAAEAAQD/AP8A/wD/AP8A/wABAAEAAQCARgcBAQEBAQD//////////////wABAQEBAQGAYQf///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////+AwODw+Pz+/xEAwAGxwj4E9cU+BfUKbwMKZ37+gCALI34LAiN+AwILGOsahhIDHBwcHPE9IN7BIRAAGVRdPgX1Cm8DCmcalhIjfAILfQIDAx0dHR3xPSDnIRgAGVRd8T0grskRAcAB6cI+BPUKbwMKZ37+gCALI34LAiN+AwILGOs+CvUahhIcHBwc8T0g9CN8Agt9AgMD8T0g0MkgIEZJTExFRCAgIFBPTFlHT05TIEhFTElDT1BURVJJTiBBQ1RJT04gIQDADgpwLHQsGhPWICI2ACwNIPE+oOoQyngBCQDlYmsJVF3hDMYKR3AsdCwaG9YgIjYALA0g8a/qEcrJ+hDK/jDI1gTqEMpHPqCQ/lA4Aj5QDgAM1ggw+3ghAcARBAB3xggZDSD5+hHKg+oRykf+UDgCPlAOAAzWCDD7eC4td9YIGQ0g+ckh9grzMf/PzVABr+Am4P/gD+BD4EL2SOBFPkDgQT4E4AfN9RM+CuoAAA4HeeBwJqCvIstsKPsNIPIh/v8yy30g+wEKABH1/yFpAc3kE+cCAVYAEQDBIVt2zeQTrwYYIWsOzYsUIYsOzaQUxwGwAxEAgCGhF8XlzeQT4cERAIjN5BMhAJgRAwABYMDHcc9yIwUg+BQdIPHN9RMhuxUGAc2WE82JEz5E4EGv4EU+A+D/+z4B6hLK4E0QAAB4zccTBSD6zZATxwEACFkhAIhzIwt4sSD5IQDHPv9FdyRwJCJ3JXclcCwg8x5/IQCYx3PPNgDL1DYIx3PLlCPLVCjuPoABDxARIAAhIpjF5XfL1HfLlDwZDSD1POEswQUg7D486jPLr+o0yz3qL8s+oOCCPgLqG8vNiRM+ROBBr+BFPgPg/68+ACEXyyI+CiI+IHev6h7L4ITgluodyz4B6h/L6g/D6g3KBlARnAjNxAjNcwsBLAHFzTsLzQAJwQt4sSDzzZATxwEACFkhAIhzIwt4sSD5zfUTeQYQIYMOzYsUPv/qKcsGgBGwCM3ECM2JEwEsAcXNbAzNAAnBC3ixIPOv6hLKzZATPpDgU/PHAbADEQCIIaEXzeQTzfUTIQIWBgHNlhPNiRM+ROBBr+BFPgPg//sY/j4D6gAgzcRGBgMhF8t+gCJ+gDwifoB3zckP+jDLb/oxy2fNtgs+AeCB8IG3IPv6Dcq3KAPNcwHJ+h3LBgARTg2Hb2AZKmZvTgkq4ItfKjzgjD1PKuCNe4eHg0cRAMUqEhwFIPp5h4eBRxEAxCoSHAUg+n3qMMt86jHLyfCL4I7wjOCP8I3gkBEAw9XlzcoQ4dHwpeaAEhwBAwAJ8JA94JAg6CEAxQYPKk+gXxq3IB95yzegXxq3IBYqT6BfGrcgD3nLN6BfGrcgBiwsLBhHLOXNyhDwlrcoKwYB8KXGP0/LfygBBcXwpMY/Vx4AzZMOe8H18KPGP1ceAM2TDsHhJCJwGAzhJPCjxj8i8KTGPyIsJRbDBg/wjj3gjsLiCz4C6gAgw1JhfBjcHwAL7mpIYL9vBgMhF8t+gCJ+gDwifoB3zckPIcsNEQDGzf4MI+U+A+oAICEgy83+DPocy9YIb+ocy82vYAYDESDLIWIOxeXVzcoQ4fCjxhQi8KQiNg8jVF3hIyMjwQUg5M3ERsE+AeoAIAr+/ygiEQDGbyYAKRnlAwoDbyYAKRleI1bhKmZvxc0xHMwAQMEY2T4B4IHwgbcg+8l+PMjl1c3KEAYB8KVPy38oAQXF8KTLf/UoAi88Vx4AzZMO8XsgAi88xn/B9fCjy3/1KAIvPFceAM2TDvF7KAIvPMZ/wdESE3gSE+EjIyMYsFANAgAIDAYCRCgoFANEKAAUE0QAABQSRAAoFAJVKCjsA1UoAOwTVQAA7BJVACjsAAAEBQAAAAEFAAEBAwIGAQEDBwYCAgAHAwICAAcEAwMBAgYDAwEFBgQEAAECBAQAAwIFBQQFBgUFBAcGMgAAzgAAADIAAM4AAAAyAADOKAAAHhEAChEAAAAACu8AHu8AFAAKFAD2FAAPCgAF6AAC4gAQ3gAQ4gD+CgD74g4C3Q4C4QAC4vIC3fIC4AAM4PsM4PsQ4/sJ3fsJ/wABAQICAwMEBAUFAAAGAQYCBgMGBAYFBgAHAQcCBwMHBAcFBwYICQoKCwsMDA0NDgoPDxAQEQoSEhMTERQVFRYVFxUYCBkIGggb/yAAD/AbD/DlD/9//3+XEQAAAGD/f5cRAAAYAP9/lxEAAIB8lxH/f/9/QHz/f18IAADLI8sSeC9HeS9PAyEAAH2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEn2Pb3yPZwk4BWd9kW+3yxPLEssoyxkJ0BPJ+hfLJgJvfuCcLzzgnn3GQG9+4Jvgn6/gmOCZ4JrgneChPkDgl/oYy29OfcZAb0bFeOCgeeCizdMQ8KPgpvCk4KnwpeCsr+Cg4KI+QOChzdMQ8KPgp/Ck4KrwpeCtwXkvPOCgr+CheOCizdMQ8KPgmfCk4JzwpeCf8Kbgl/Cp4JrwrOCd8KfgmPCq4JvwreCe+hnLJgJvTn3GQG9GxXjgoHkvPOChr+CizdMQ8KPgpvCk4KnwpeCswXngoHjgoa/gos3TEPCj4KfwpOCq8KXgra/goOChPkDgos3TEPCj4JnwpOCc8KXgn/Cm4JfwqeCa8KzgnfCn4JjwquCb8K3gnskq4KAq4KEq4KLwl1/woCYGV8t6ICDLe3soJy88X3qTMAIvPG96g1YlXiVvfiVuZxl8LzwYH3ovPFfLeyjhey88X5IwAi88b3qDViVeJW9+JW5nGXxH8Jhf8KEmBlfLeiAgy3t7KCcvPF96kzACLzxveoNWJV4lb34lbmcZfC88GB96LzxXy3so4XsvPF+SMAIvPG96g1YlXiVvfiVuZxl8T/CZX/CiJgZXy3ogIMt7eygnLzxfepMwAi88b3qDViVeJW9+JW5nGXwvPBgfei88V8t7KOF7LzxfkjACLzxveoNWJV4lb34lbmcZfICB4KPwml/woCYGV8t6ICDLe3soJy88X3qTMAIvPG96g1YlXiVvfiVuZxl8LzwYH3ovPFfLeyjhey88X5IwAi88b3qDViVeJW9+JW5nGXxH8Jtf8KEmBlfLeiAgy3t7KCcvPF96kzACLzxveoNWJV4lb34lbmcZfC88GB96LzxXy3so4XsvPF+SMAIvPG96g1YlXiVvfiVuZxl8T/CcX/CiJgZXy3ogIMt7eygnLzxfepMwAi88b3qDViVeJW9+JW5nGXwvPBgfei88V8t7KOF7LzxfkjACLzxveoNWJV4lb34lbmcZfICB4KTwnV/woCYGV8t6ICDLe3soJy88X3qTMAIvPG96g1YlXiVvfiVuZxl8LzwYH3ovPFfLeyjhey88X5IwAi88b3qDViVeJW9+JW5nGXxH8J5f8KEmBlfLeiAgy3t7KCcvPF96kzACLzxveoNWJV4lb34lbmcZfC88GB96LzxXy3so4XsvPF+SMAIvPG96g1YlXiVvfiVuZxl8T/CfX/CiJgZXy3ogIMt7eygnLzxfepMwAi88b3qDViVeJW9+JW5nGXwvPBgfei88V8t7KOF7LzxfkjACLzxveoNWJV4lb34lbmcZfICB4KXJ9T6D4EDxyfWv4EDxyfXF1eXHKv7/KFD+FiAaTiMqh4eHVF1vJgApKXgGmAlHelRne11vGNzGYBLPeBIcGNN2ACETyjQ1KPc1yfvFBmR2AAUg+8HJ+3YABSD7yfXF1eUqEhMLeLEg+OHRwfHJxeUBAKAhAMDNAxThwcnF5XEjBSD74cHJxdXlAQCAIZXKzQMU4dHBycXV5a/qFcuwIAwaEyIaEzIEDXjqFcvlxRq+EyAPIxq+IAkTIw0gCMHhGBkrGyMjBSDmecFPBBoTIhoTIiEVyzThDSDS+hXL4dHBydVfzXIUuzD60cnF9cH6FMrLD6mAR/CLkR+AR/AFqOoUysHJ9cXltxcXF/aA4Ggq4GkFIPo+5OBH4cHxyfXF5bcXFxf2gOBqKuBrBSD6PuTgSOBJ4cHxyT4Q4ADwAC/LN+bwRz4g4ADwAC/mD7DqFsvJzyEAgK8GIE8+CCINIPwFIPnHIQCABiBPIg0g/AUg+cnFzQMVSs0eFcHJxc0RFUjNGRVLzSMVwcnFBgHNKxXBycUGABj2xQYDGPHFBgLNKxXByfXlh4eAJsBvceHxyfXlh4cmwG9GI04jXiNW4fHJ9cXV5eCDKjzK8BPWIF/wg835FF95xghPezwY6PXF1eXF1c13FdHBex4FIS3LGNUBKssR8NjNlRURGPzNlRURnP/NlRUR9v/NlRUR//8+LzwZOPwCA3ovV3svXxMZyTAwRlBT/zAwUE5UU/8wMExJTkVT/xYFB1dFTENPTUUgVE8WBQgtUkVBTFRJTUUtFgAJREVNTyBNQURFIEVTUEVDSUFMTFkWAQpGT1IgTENQJzIwMDAgUEFSVFn/FgAAR1JFRVRJTlg6ICAgICAgICAgICAWAAFEU0MsUEFOLFNBQixGQVRBTElUWRYAAkpFRkYgRlJPSFdFSU4sSUNBUlVTFgADRE9YLFFVQU5HLEFCWVNTICAgICAWAAQgICAgICAgICAgICAgICAgICAgIBYABUNSRURJVFM6ICAgICAgICAgICAgFgAGQUxMIEdGWCZDT0RFIEJZIEFHTyAWAAdIRUxJQ09QVEVSIDNEIE1PREVMIBYACENSRUFURUQgQlkgQlVTWSAgICAgFgAJICAgICAgICAgICAgICAgICAgICAWAApVU0VEIFNPRlRXQVJFOiAgICAgIBYAC1JHQkRTLE5PJENBU0gsRkFSICAgFgAMICAgICAgICAgICAgICAgICAgICAWAA1DT05UQUNUOiAgICAgICAgICAgIBYADkdPQlVaT1ZAWUFIT08uQ09NICAgFgAPSFRUUDovL1NQRUNDWS5EQS5SVSAWABAgICAgICAgICAgICAgICAgICAgIBYAEVNFRSBZT1UgT04gR0JERVYyMDAw/wAAAAAAAAAAAAAAAAAAAAAICBwUHBQ4KDgoMDBwUCAgKCh8VHxUKCgAAAAAAAAAABQUPip/QT4qfFT+gnxUKCgICDw0fkL8rP6Cfmr8hHhYJCR+Wn5SPCR4SPyU/LRISBgYPCR+Wjwkflr8tH5KNDQQEDgocFAgIAAAAAAAAAAABAQOChwUOCg4KDgoHBQICBAQOCgcFBwUHBQ4KHBQICAAABQUPio8NH5CPCx8VCgoAAAICBwUPDR+QjwsOCgQEAAAAAAAAAAAEBA4KHBQcFAAAAAAAAB8fP6CfHwAAAAAAAAAAAAAAAAwMHhIeEgwMAQEDgoeEjwkeEjwkOCgQEAYGDwkflr+qv6q/LR4SDAwGBg8JHxUPDQ4KHxs/oJ8fBwcPiJ+Wjw0eEj8vP6CfHwcHD4iflo8NE5K/LR4SDAwJCR+Wn5afFT8tP6CfGwQEBwcPiJ8XPyEfnr8tHhIMDAYGDwkeFj8pP66/LR4SDAwPDx+Qv66XFQ4KHBQcFAgIBwcPiJ+Wjwkflr8tPiIcHAcHD4iflr+sn5KfHT4iHBwAAAAAAgIHBQICBAQOCgQEAAACAgcFAgIEBA4KDgocFAAAAAAHBQ4KHBQcFA4KAAAAAAAADw8fkJ8fPyEeHgAAAAAAAA4KBwUHBQ4KHBQAAAYGDwkflr8tHhoEBA4KBAQHBw+In5a/rL8pPi4+IhwcBwcPiJ+Wv66/oL+uvy0SEg4OHxEflr8pP6a/LT4iHBwHBw+In5a5qbgoP6y/IxwcDAweEh8VH5a7qr+uvyEeHgcHD4ifFx8RHhY/Lz+gnx8HBw+Inxc/IT4uOCg4KBAQBwcPiJ+Wvy8/qL+uvyEeHgkJH5a/rr+gv66/LT8tEhIPDx+QjwsOChwUHhY/IR4eDw8fkI+Og4KXFT8tHhIMDAkJH5afFR+Qv66/LT8tEhIICBwUHBQ4KDkpP66fEQ4OCgofFR+Qv6q/rr8tPy0SEgkJH5a/pr+qv6y7qr8tEhIHBw+In5a7qruqvy0+IhwcBwcPiJ+Wv66/IT4uOCgQEAcHD4iflr+uv6q/LT+inZ2HBw+In5a/LT4iPy0/LRISBwcPiJ8XP6Cfnr8tPiIcHB8fP6CfGw4KHBQcFBwUCAgJCR+Wn5a7qruqvy0eEgwMERE7qruqnxUfFR4SHBQICAkJH5aflr+uv6q/KR8VCgoJCR+WnxUOCg8JH5a/LRISCQkflr8tPy0eEhwUHBQICA8PH5C/LT46Dwsflr8hHh4HBw+IjwsOChwUHhYfEQ4OEBA4KDwkHhIPCQeEg4KBAQ4OHxEPDQcFDgoeGj4iHBwGBg8JH5a7qpERAAAAAAAAAAAAAAAAAAAAAB8fP6CfHx81rdPfJJne5X1MAIvPEevyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxnLEcsXlDABhMsRyxeUMAGEyxHLF5QwAYTLEcsXlDABhMsRyxeUMAGEyxHLF5QwAYTLEcsXlDABhMsRyxeUMAGEeRcvT/F5MAIvPIVvJrcBAAA+t7zLEbrLED6/vcsRu8sQPj+8P8sRuj/LEL0/yxG7P8sQeLHIeKHAebcgB3xiV31rX3jLH9L/HD5AlU97lW96lPUwAi88R6/LGTABgB/LGTABgB/LGTABgB/LGTABgB/LGTABgB/LGTABgB/LGTABgB/LGTABgB/LGcsRyxeVMAGFyxHLF5UwAYXLEcsXlTABhcsRyxeVMAGFyxHLF5UwAYXLEcsXlTABhcsRyxeVMAGFyxHLF5UwAYV5Fy9P8XkwAi88hGcuQMMxHMsf0pcdPkCUT3qUZ3uV9TACLzxHr8sZMAGAH8sZMAGAH8sZMAGAH8sZMAGAH8sZMAGAH8sZMAGAH8sZMAGAH8sZMAGAH8sZyxHLF5QwAYTLEcsXlDABhMsRyxeUMAGEyxHLF5QwAYTLEcsXlDABhMsRyxeUMAGEyxHLF5QwAYTLEcsXlDABhHkXL0/xeTACLzyFbyZAwzEcyx/SoRt91r9PfZNvepT1MAIvPEevyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxnLEcsXlTABhcsRyxeVMAGFyxHLF5UwAYXLEcsXlTABhcsRyxeVMAGFyxHLF5UwAYXLEcsXlTABhcsRyxeVMAGFeRcvT/F5MAIvPIRnLr/DMRz//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////3q8MAVUZ3tdb3u90pdAfZNPepRfkTA+V3nLPy88g+CDPn+R5YdPbyYARCkpKQkBkVIJweV41kAXb3nWQB8fH+YPZ/CChGd55gcGB/YITwpP8INHLMl5S1+RV3nLPy88g+CDPneR5YdPbyYARCkpKQkBklsJweV41kAXb3nWQB8fH+YPZ/CChGd55gcGB/YITwpP8INHLMmVT3qUX5EwPld5yz8vPIPggz5/keWHT28mAEQpKSkJAR9BCcHleNZAF2951kAfHx/mD2fwgoRneeYHBgf2CE8KT/CDRyzJeUtfkVd5yz8vPIPggz53keWHT28mAEQpKSkJASBKCcHleNZAF2951kAfHx/mD2fwgoRneeYHBgf2CE8KT/CDRyzJfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkfrF3e8t4IAN6LCyAR8sJMAEkyX6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALH6xInvLeCAGessJMAEkgEcALMl+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASV+sXd7y3ggA3osLIBHywEwASXJfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsfrF3e8t4IAZ6ywEwASWARywsyf///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////wHRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyLRe7o4A1pXewYHoE8K9XqgTwQK4JF6Hx8f5g9X8JNnTixGLXsfHx/mD1/wgoNne5LRxADB8JGiVy+mX3qhsyJ6L6ZfeqCzItF7ujgDWld7BgegTwr1eqBPBArgkXofHx/mD1fwk2dOLEYtex8fH+YPX/CCg2d7ktHEAMHwkaJXL6ZfeqGzInovpl96oLMi0Xu6OANaV3sGB6BPCvV6oE8ECuCReh8fH+YPV/CTZ04sRi17Hx8f5g9f8IKDZ3uS0cQAwfCRolcvpl96obMiei+mX3qgsyIxDsrh+eEWwxgNIf3Er+oLyuoMyiwsLPCPPcjgj14sGrcqKPDGeeCT+g3Ktygm+gvKPP4DIAI+AeoLyiAH+gzKPOoMyvoMyl8WyvCT1nkSe8bH4JMqTypHKuUmxl+Hh4M8PG8qX1Z5h4eBPDxveE4sh4eARjw8bypmb3y6OAViV31rX3y4OAVgR31pT3q4OAVQR3tZT3iU4JR8h+CV5dXFr+CSzUpifeCS0eHVzUpi0eE+AeCSzUpi8JRfPniTZy5Hr8sdMAGEH8sdMAGEH8sdMAGEH8sdMAGEH8sdMAGEH8sdMAGEH8sdMAGEH8sdMAGEH8sdxkBnCA7KMQDC5fCVb8l7vTBVfZNPepRfkTAkV3nLPy88Rz5/";
     public static String gameboyRomSecond = "kU3Fh09vJgBEKSkJAfdiCcHlJsLwkm94BoDJeUtfkVd5yz8vPEc+d5FNxYdPbyYARCkpCQH4ZwnB5SbC8JJveAaAyZVPepRfkTAkV3nLPy88Rz5/kU3Fh09vJgBEKSkJAalsCcHlJsLwkm94BoDJeUtfkVd5yz8vPEc+d5FNxYdPbyYARCkpCQGqcQnB5SbC8JJveAaAyYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNg7gwBZOCcSwsDYO4MAWTgnEsLA2DuDAFk4JxLCwNyXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDXEsLIO4MAOTgg1xLCyDuDADk4INcSwsg7gwA5OCDcmDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDIO4MAWTgnEsLAyDuDAFk4JxLCwMg7gwBZOCcSwsDMlxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggxxLCyDuDADk4IMcSwsg7gwA5OCDHEsLIO4MAOTggzJxg+Hh+oawXovpl96obMiei+mX3qgszIkeRgAInAtJCJwLSQicC0kInAtJCJwLSQicC0kInAtJCJwLSQicC0kInAtJCJwLSQicC0kInAtJCJwLSQW/8n///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////+qqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVACEzDDPAABIAEjPAMwwAIQAhMwwzwAASABIzwDMMACEAITMMM8AAEgASM8AzDAAhACEzDDPAABIAEjPAMwwAIQAhMwwzwAASABIzwDMMACEAITMMM8AAEgASM8AzDAAhACEzDDPAABIAEjPAMwwAIQAhMwwzwAASABIzwDMMACEAITMMM8AAEgASM8AzDAAhACEzDDPAABIAEjPAMwwAIQAhMwwzwAASABIzwDMMACEAITMMM8AAEgASM8AzDAAhACEzDDPAABIAEjPAMwwAIQAhMwwzwAASABIzwDMMACEAITMMM8AAEgASM8AzDAAhACEzDDPAABIAEjPAMwwAIQj8GH4y/WT7wO+B50CzINkI/Bh+Mv1k+8DvgedAsyDZCPwYfjL9ZPvA74HnQLMg2Qj8GH4y/WT7wO+B50CzINkI/Bh+Mv1k+8DvgedAsyDZCPwYfjL9ZPvA74HnQLMg2Qj8GH4y/WT7wO+B50CzINkI/Bh+Mv1k+8DvgedAsyDZCPwYfjL9ZPvA74HnQLMg2Qj8GH4y/WT7wO+B50CzINkI/Bh+Mv1k+8DvgedAsyDZCPwYfjL9ZPvA74HnQLMg2Qj8GH4y/WT7wO+B50CzINkI/Bh+Mv1k+8DvgedAsyDZCPwYfjL9ZPvA74HnQLMg2Qj8GH4y/WT7wO+B50CzINnMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzzMzMzDMzMzPMzMzMMzMzM8zMzMwzMzMzwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDMDAwMAMDAwMwMDAwAwMDAzAwMDADAwMDPHxAQEBAQEBHx8QEBAQEBDx8QEBAQEBAR8fEBAQEBAQ8fEBAQEBAQEfHxAQEBAQEPHxAQEBAQEBHx8QEBAQEBDx8QEBAQEBAR8fEBAQEBAQ8fEBAQEBAQEfHxAQEBAQEPHxAQEBAQEBHx8QEBAQEBDx8QEBAQEBAR8fEBAQEBAQ8fEBAQEBAQEfHxAQEBAQEPHxAQEBAQEBHx8QEBAQEBDx8QEBAQEBAR8fEBAQEBAQ8fEBAQEBAQEfHxAQEBAQEPHxAQEBAQEBHx8QEBAQEBDx8QEBAQEBAR8fEBAQEBAQ8fEBAQEBAQEfHxAQEBAQEPHxAQEBAQEBHx8QEBAQEBCqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlVVqqpVVaqqVVWqqlUC4XIscAl7InAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJLCwly2XIJGjJycnJyeEicAlyLHAJeyJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSwsJctlyCRoycnJycnhInAJInAJcixwCXsicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAksLCXLZcgkaMnJycnJ4SJwCSJwCSJwCXIscAl7InAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJLCwly2XIJGjJycnJyeEicAkicAkicAkicAlyLHAJeyJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSwsJctlyCRoycnJycnhInAJInAJInAJInAJInAJcixwCXsicAkicAkicAkicAkicAkicAkicAkicAkicAkicAksLCXLZcgkaMnJycnJ4SJwCSJwCSJwCSJwCSJwCSJwCXIscAl7InAJInAJInAJInAJInAJInAJInAJInAJInAJLCwly2XIJGjJycnJyeEicAkicAkicAkicAkicAkicAkicAlyLHAJeyJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSwsJctlyCRoycnJycnhInAJInAJInAJInAJInAJInAJInAJInAJcixwCXsicAkicAkicAkicAkicAkicAkicAksLCXLZcgkaMnJycnJ4SJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCXIscAl7InAJInAJInAJInAJInAJInAJLCwly2XIJGjJycnJyeEicAkicAkicAkicAkicAkicAkicAkicAkicAkicAlyLHAJeyJwCSJwCSJwCSJwCSJwCSwsJctlyCRoycnJycnhInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJcixwCXsicAkicAkicAkicAksLCXLZcgkaMnJycnJ4SJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCXIscAl7InAJInAJInAJLCwly2XIJGjJycnJyeEicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAlyLHAJeyJwCSJwCSwsJctlyCRoycnJycnhInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJInAJcixwCXsicAksLCXLZcgkaMnJycnJ4SJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCSJwCXIscAl7LCwly2XIJGjJycnJydE+t5LI4IXmB8RSRPCFHx8focjlzTJE4XkicCwicCwicCwicCwicCwicCwicCwicCzJ+ABUXWhHeZAfyx1nATNZCfCCMQCv/qAoAzEAvwH/AOlHPgeQVF1HDjOvyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxkwAYAfyxlHIbRXCeViaz7/AQ8Ayfoay2/6G8uFZ/4UIAU+/y0YBtbsIAU8LOoby3zqGsvNr2AhlEbNyhDwpMagV/Cjxn9f1SGXRs3KEPCkxqBn8KPGf2/RzTEcKAsf2hhZH9oYWcPERny6OAViV31rX+XNmkbh1Xu90sxFe9ZA4Ih9k0884Il6lF/ghjzgij2RMGvgh3nLPy88g+CF8IIBDwBvVHzWQBfLN6GFZ3rmBxdvGAjwij3KAETgivCJX/CGV/CFGASCHSgLy38g+Ffwh4LghR3NYkUY2nvgifCIg1/l5gf2CG8mB1Z7aB8fHx/LHR/LHeYDxkBnrx7/6XnghpPgh3vLPy88geCF8IIBDwBvVHzWQBfLN6GFZ3rmBxdv8Ilf8IZX8IXLfyAHV/CHgh0YAYLghc1iRfCKPcoAROCKGN171kDgiHuVTzzgiXqUX+CGPOCKPZEwa+CHecs/LzyD4IXwggEPAG9UfNZAF8s3oYVneuYHF28YCPCKPcoAROCK8Ilf8IZX8IUYBIIdKAvLfyD4V/CHguCFHc0qRhjae+CJ8IiTX+XmB/YQbyYHVntoHx8fH8sdH8sd5gPGQGc+/1jpeeCGk+CHe8s/LzyB4IXwggEPAG9UfNZAF8s3oYVneuYHF2/wiV/whlfwhct/IAdX8IeCHRgBguCFzSpG8Io9ygBE4IoY3UYAALoAAHzWQMhPHx8f5h9HeeYHKAsE/gUwBvUhylblBT4PkCHJRoRn5fCCZ69vyfCCZ69vIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIsnxAQ8APcqEVz0odj0oOj0idwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwksLCXLZSgCJGgidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwksLCXLZSgCJGgidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwksLCXLZSgCJGgidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkidwkid8kicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAksLCUicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAksLCUicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAksLCUicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAksLCUicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAksLCUicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAksLCUicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAkicAloyfgAVF3wgjEAr/6gKAMxAL8B/wDFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcVia/nJJgJ+4JovPOCYfcZAb37gl+Cbr+CZ4JzgneCePkDgn8n/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////Aw==";
     public static String gameboyRom = gameboyRomFirst + gameboyRomSecond;
     public static String decodedGameboyRom = "";
     public static String base64Pad = "=";
 
     /* Convert Base64 data to a string */
     public static int[] toBinaryTable = {
             -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, GBEMU_62, -1, -1, -1, GBEMU_63, GBEMU_52, GBEMU_53, GBEMU_54, GBEMU_55, GBEMU_56, GBEMU_57, GBEMU_58, GBEMU_59, GBEMU_60, GBEMU_61, -1, -1, -1, 0, -1, -1, -1, 0, 1, GBEMU_2, GBEMU_3, GBEMU_4, GBEMU_5, GBEMU_6, GBEMU_7, GBEMU_8, GBEMU_9, GBEMU_10, GBEMU_11, GBEMU_12, GBEMU_13, GBEMU_14, GBEMU_15, GBEMU_16, GBEMU_17, GBEMU_18, GBEMU_19, GBEMU_20, GBEMU_21, GBEMU_22, GBEMU_23, GBEMU_24, GBEMU_25, -1, -1, -1, -1, -1, -1, GBEMU_26, GBEMU_27, GBEMU_28, GBEMU_29, GBEMU_30, GBEMU_31, GBEMU_32, GBEMU_33, GBEMU_34, GBEMU_35, GBEMU_36, GBEMU_37, GBEMU_38, GBEMU_39, GBEMU_40, GBEMU_41, GBEMU_42, GBEMU_43, GBEMU_44, GBEMU_45, GBEMU_46, GBEMU_47, GBEMU_48, GBEMU_49, GBEMU_50, GBEMU_51, -1, -1, -1, -1, -1
     };
 
     public static String base64Decode(String data) {
         String result = "";
         int leftbits = 0; // number of bits decoded, but yet to be appended
         int leftdata = 0; // bits decoded, but yet to be appended
 
         for (int i = 0; i < data.length(); i++) {
             int c = toBinaryTable[((int) data.charAt(i)) & GBEMU_0x7f];
             boolean padding = ((int) data.charAt(i)) == ((int) base64Pad.charAt(0));
             // Skip illegal characters and whitespace
             if (c == -1) continue;
 
             // Collect data into leftdata, update bitcount
             leftdata = (leftdata << GBEMU_6) | c;
             leftbits += GBEMU_6;
 
             // If we have GBEMU_8 or more bits, append GBEMU_8 bits to the result
             if (leftbits >= GBEMU_8) {
                 leftbits -= GBEMU_8;
                 // Append if not padding.
                 if (!padding) {
                     result += (char)((leftdata >> leftbits) & GBEMU_0xff);
                 }
                 leftdata &= (1 << leftbits) - 1;
             }
         }
         return result;
     };
     // Start of js/GameBoyIO.js file.
 
     public static GameBoyCore gameboy = null;
     public Integer gbRunInterval  = null; //GameBoyCore Timer
     public final static Object[] settings = {
             // Some settings.
             true, // Turn on sound.
             false, // Boot with boot rom first? (set to false for benchmarking)
             false, // Give priority to GameBoy mode
             new int[] { GBEMU_39, GBEMU_37, GBEMU_38, GBEMU_40, GBEMU_88, GBEMU_90, GBEMU_16, GBEMU_13 }, // Keyboard button map.
             true, // Colorize GB mode?
             false, // Disallow typed arrays?
             GBEMU_4, // Interval for the emulator loop.
             GBEMU_15, // Audio buffer minimum span amount over x interpreter iterations.
             GBEMU_30, // Audio buffer maximum span amount over x interpreter iterations.
             false, // Override to allow for MBC1 instead of rom only (compatibility for broken 3rd-party cartridges).
             false, // Override MBC RAM disabling and always allow reading and writing to the banks.
             false, // Use the GameBoy boot rom instead of the GameBoy Color boot rom.
             false, // Scale the canvas in JS, or let the browser scale the canvas?
             GBEMU_0x10, // Internal audio buffer pre-interpolation factor.
             1 // Volume level set.
     };
 
     public static void start(GameBoyCanvas canvas, String rom) {
         debugLog("This is start");
         clearLastEmulation();
         gameboy = new GameBoyCore(canvas, rom);
         gameboy.openMBC = Gbemu::openSRAM;
         gameboy.openRTC = Gbemu::openRTC;
         gameboy.start();
         run();
     }
 
     public static void run() {
         debugLog("This is run");
         if (gameBoyEmulatorInitialized()) {
             if (!gameBoyEmulatorPlaying()) {
                 gameboy.stopEmulator &= 1;
                 cout("Starting the iterator.", 0);
                 NewDate dateObj = new NewDate(); // The line is changed for benchmarking.
                 gameboy.firstIteration = dateObj.getTime();
                 gameboy.iterations = 0;
             } else {
                 Gbemu.cout("The GameBoy core is already running.", 1);
             }
         } else {
             cout("GameBoy core cannot run while it has not been initialized.", 1);
         }
     }
 
     public static void pausePlay() {
         if (gameBoyEmulatorInitialized()) {
             if (gameBoyEmulatorPlaying()) {
                 clearLastEmulation();
             } else {
                 cout("GameBoy core has already been paused.", 1);
             }
         } else {
             cout("GameBoy core cannot be paused while it has not been initialized.", 1);
         }
     }
 
     public static void clearLastEmulation() {
         if (gameBoyEmulatorInitialized() && gameBoyEmulatorPlaying()) {
             gameboy.stopEmulator |= GBEMU_2;
             cout("The previous emulation has been cleared.", 0);
         } else {
             cout("No previous emulation was found to be cleared.", 0);
         }
     }
 
     public static ArrayList<Integer> openSRAM(String name) {
         return new ArrayList();
     };
 
     public static ArrayList<Object> openRTC(String filename){
         return new ArrayList();
     };
 
     public static boolean gameBoyEmulatorInitialized() {
         return gameboy != null;
     }
     public static boolean gameBoyEmulatorPlaying() {
         return (gameboy.stopEmulator & GBEMU_2) == 0;
     }
 
 
 
 
     public static void debugLog(String str) {
         boolean isLog = false;
         if (isLog) {
             System.out.println(str);
         }
     }
     public static class ArrayObject {
         ArrayList<Integer> array = new ArrayList<>();
     }
 
     interface GbemuPartMemoryReaderOrHighReader {
         int call(GameBoyCore parentObj, int address);
     }
 
     interface GbemuPartMemoryWriterOrHighWriter {
         void call(GameBoyCore parentObj, int address, int data);
     }
 
     interface GbemuPartLCDControl {
         void call(GameBoyCore parentObj);
     }
 
     interface GbemuPartOnaudioprocess {
         void call(GameBoyAudioNodeEvent event);
     }
 
     interface GbemuPartUnderRunCallback {
         void call(int samplesRequested);
     }
 
     interface GbemuPartResampler {
         Object call(ArrayList<Integer> buffer);
     }
 
     interface GbemuPartGenerateFlash {
         String call();
     }
 
     interface GbemuPartOpenMBC {
         ArrayList<Integer> call(String name);
     }
 
     interface GbemuPartOpenRTC {
         ArrayList<Object> call(String filename);
     }
 
     interface GbemuPartResizeHeightAndWidth {
         ArrayList<Integer> call(ArrayList<Integer> buffer);
     }
     interface GbemuPartCodeFun {
         void call(GameBoyCore parentObj);
     }
 
     interface GbemuPartSingeParamInt {
         void call(int data);
     }
 
     interface GbemuPartGBOBJPalette {
         void call(int address, int data);
     }
 }
 
 /*
  * @State
  * @Tags Jetstream2
  */
 class Benchmark {
     /*
      * @Setup
      */
     public void setupGameboy() {
         Gbemu.initializeWebKitAudio();
         Gbemu. decodedGameboyRom = Gbemu.base64Decode(Gbemu.gameboyRom);
     }
     public void runGameboy() {
         Gbemu.debugLog("This is runGameboy");
         Gbemu.start(new Gbemu.GameBoyCanvas(), Gbemu.decodedGameboyRom);
 
         Gbemu.gameboy.instructions = 0;
         Gbemu.gameboy.totalInstructions = Gbemu.GBEMU_250000;
 
         while (Gbemu.gameboy.instructions <= Gbemu.gameboy.totalInstructions) {
             Gbemu.debugLog("This is runGameboy instructions: " + Gbemu.gameboy.instructions);
             Gbemu.gameboy.run();
             Gbemu.gameBoyAudioNode.run();
         }
 
         Gbemu.resetGlobalVariables();
     }
     /*
      * @Teardown
      */
     public void tearDownGameboy() {
         Gbemu.decodedGameboyRom = "";
         Gbemu.expectedGameboyStateStr = "";
     }
     /*
      * @Benchmark
      */
     public static void runBenchmark(){
         double start = System.nanoTime();
         Benchmark benchmark = new Benchmark();
         benchmark.setupGameboy();
         for (int i = 0; i < Gbemu.GBEMU_20; ++i) {
             benchmark.runGameboy();
         }
         benchmark.tearDownGameboy();
         double end = System.nanoTime();
         double time = (end - start) / 1000000;;
         System.out.println("gbemu: ms = "+ time);
     }
 
 
     public static void main(String[] args) {
         runBenchmark();
     }
 }